Regreso con este tema porque para un proceso requiero leer muchos archivos xml, el tema es el siguiente:
con COM MSXML2.DomDocument tarda en leer poco más de 8000 archivos 1hora 20minutos aproximado, esto es parte del código:
Code: Select all
oCFDI := Win_OleCreateObject( "MSXML2.DomDocument" )
FOR EACH archivo IN hb_vfDirectory( rutaBase + "*.xml" )
i++
IF hb_vfExists( archivoXML := rutaBase + archivo[ F_NAME ] )
oCFDI:Load( archivoXML )
? "Procesando archivo: " + archivoXML + " " + hb_NtoS(i) + " de " + hb_NtoS( Len( hb_vfDirectory( rutaBase + "*.xml" ) ) )
olNode := oCFDI:selectSingleNode("//cfdi:Comprobante/cfdi:Complemento/tfd:TimbreFiscalDigital")
IF hb_IsNil( olNode )
? hb_Utf8ToStr( "No se encontro el nodo TimbreFiscalDigital" )
ELSE
cUUID := olNode:getAttribute("UUID")
hb_fNameSplit( archivoXML, NIL, @cName, @cExt )
cXML := cName + cExt
cQry := "INSERT INTO ArchivosXML (Archivo, UUID) " + ;
"VALUES (" + ;
convertToSQL( cXML ) + ", " + ;
convertToSQL( cUUID ) + " )"
BEGIN SEQUENCE WITH {|oError| BREAK( oError ) }
oConnection:Execute( cQry )
RECOVER USING oError
? "Error al actualizar datos en la tabla" + E"\n" + oError:Description
RETURN NIL
END SEQUENCE
ENDIF
ENDIF
NEXT
Después de leer algunos artículos que mencionan que hay algunos problemas en el uso de memoria con createobject, pasé a la segunda opción que es utilizar la lib miniXML
Perooo para mi sorpresa utiliza más tiempo en leer la misma cantidad de archivos, el tiempo de lectura es de 2horas 20minutos

, este es parte del código utilizando miniXML:
Code: Select all
FOR EACH cFile IN aDir
IF hb_fileExists( cFileName := cPath + cFile[ F_NAME ] )
? "Procesando archivo: " + cFileName + " " + hb_NtoS( nFile ) + " de " + hb_NtoS( nLenDir )
xmlBuffer := hb_memoRead( cFileName )
body := mxmlLoadString( NIL, xmlBuffer, MXML_OPAQUE_CALLBACK )
IF Empty( hTimbreFiscal := mxmlFindElement( body, body, "tfd:TimbreFiscalDigital",,, MXML_DESCEND ) )
? "Unable to find <tfd:TimbreFiscalDigital> elment in XML!" + hb_eol()
crearLogArchivo( cArchivoLog, "Archivo XML sin complemento! " + cFileName + hb_Eol(), @lNuevo )
mxmlDelete( body )
ELSE
mxmlGetElement( hTimbreFiscal )
cUUID := mxmlElementGetAttr( hTimbreFiscal, "UUID" )
IF hb_IsNIl( cUUID )
mxmlDelete( body )
? "No existe el atributo UUID!!!" + hb_eol()
ELSE
? "UUID: " + cUUID
?
hb_fNameSplit( cFileName, NIL, @cName, @cExt )
cXMLFile := cName + cExt
cQry := "INSERT INTO ArchivosXML (Archivo, UUID) " + ;
"VALUES (" + ;
convertToSQL( cXMLFile ) + ", " + ;
convertToSQL( cUUID ) + " )"
BEGIN SEQUENCE WITH {|oError| BREAK( oError ) }
oConn:Execute( cQry )
RECOVER USING oError
? "Error al actualizar datos en la tabla" + E"\n" + oError:Description
RETURN NIL
END SEQUENCE
mxmlDelete( body )
ENDIF
ENDIF
ENDIF
++nFile
NEXT
Así que no como no estoy conforme con los resultados obtenidos, realicé un pequeño programa en el lenguaje C# y mi SORPRESA es que con la misma cantidad de archivos tarda el proceso SÓLO 20 segundos

... y la locura es que corrí el proceso para que leyera más de 150mil archivos y SÓLO tardó 5 minutos.
Así que tengo algunas preguntas:
- En los fragmentos de códigos de mis soluciones con Harbour, hay forma de refactorizar para obtener mejores resultados.
- Es justo comparar la velocidad de los procesos entre los lenguajes Harbour y C#.
Agradezco sus comentarios.
Saludos,
Javier