2009-03-15 21 views
5

La situación es la siguiente: hay un archivo con 14 294 508 enteros sin signo y 13 994 397 números de coma flotante (es necesario leer double s). El tamaño total del archivo es ~ 250 MB.¿Cómo se realiza una entrada de formato rápido desde una secuencia en C++?

El uso de std::istream lleva ~ 30sec. Leer los datos de un archivo a la memoria (solo copiar bytes, sin una entrada formateada) es mucho más rápido. ¿Hay alguna manera de mejorar la velocidad de lectura sin cambiar el formato de archivo?

+0

Creo que debería publicar su código de bucle – Ben

+0

Si se trata de MSVC libs, es posible que desee investigar la penalización que está incurriendo en SECURE_SCL (activada de forma predeterminada). Pero ten cuidado de entender las implicaciones de apagarlo. – Functastic

+0

Lo sentimos, debería ser: _SECURE_SCL – Functastic

Respuesta

3

¿Necesita usar el estilo de E/S de STL? Debe verificar this excelente trabajo de uno de los expertos. Es un especializado iostream por Dietmar Kuhl.

Odio sugerir esto, pero eche un vistazo a las rutinas de E/S en formato C. Además, ¿estás leyendo todo el archivo de una vez?

+0

La sintaxis y el enfoque no importan :) Y sí, estoy leyendo todo el archivo. –

+0

¿Has probado fscanf y amigos? Yo diría darles una oportunidad, y medir. – dirkgently

1

También puede ser que desee ver en la biblioteca FastFormat de Matthew Wilson:

no he usado, pero que hace algunas afirmaciones bastante impresionantes y he encontrado un montón de su otro trabajo que vale la pena estudiar y usar (y robar en ocasiones).

+0

¿Admite entrada formateada? –

+0

Mierda, tienes razón ... Es formato de salida solamente. –

+0

Tal vez las técnicas se pueden aplicar a la entrada – dcw

1

No ha especificado el formato. Es posible que pueda mapear la memoria, o leer en grandes fragmentos y procesar en un algoritmo por lotes.

Además, no ha dicho si está seguro de que el archivo y el proceso que lo leerán estarán en la misma plataforma. Si un proceso big-endian lo escribe y un proceso little-endian lo lee, o viceversa, no funcionará.

1

La entrada de análisis solo (atoi & atof), generalmente aumenta la velocidad al menos dos veces, en comparación con los métodos de lectura "universal".

0

algo rápido y sucio es simplemente volcar el archivo en una cadena estándar de C++ y, a continuación, utilizar un stringstream en él:

#include <sstream> 
// Load file into string file_string 
std::stringstream s(file_string); 
int x; float y; 
s >> x >> y; 

Esto no le puede dar mucho de una mejora en el rendimiento (que se obtiene una mayor velocidad al evitar iostreams), pero es muy fácil de probar, y puede ser lo suficientemente rápido.

Cuestiones relacionadas