2012-05-14 16 views
7

Tengo muchos hilos que simultáneamente leen el mismo archivo (aproximadamente 100M), y solo un hilo para actualizar el archivo. Quiero asignar el archivo en la memoria para reducir el ARCHIVO de E/S. ¿Cómo se puede hacer esto en Java?¿Cómo implementar la lectura concurrente en un archivo mapeado en la memoria en Java?

que básicamente han considerado los 2 siguientes métodos:

  1. con matriz de bytes para almacenar el archivo, y cada vez crear ByteArrayInputStream para leer el búfer cuando multi-hilo de leer.
  2. con NIO para obtener un canal de archivo, sincronizó el canal para leer desde el MappedByteBuffer para lectura de múltiples hilos.

No estoy seguro de si los métodos deberían funcionar. Por favor ayuda a dar alguna pista si hay una mejor solución.

+0

Si todo el mundo está leyendo y nadie está escribiendo, no necesita sincronización en absoluto. – EJP

+0

@EJP habrá un hilo para escribir, todos los demás hilos leídos, prefiero usar ReadWriteLock en byte [] para hacer ahora. –

+0

Gracias, pero, con respecto, su pregunta no menciona escritores. Cambia la imagen por completo. Sugiero que edites ese hecho crítico en tu pregunta. – EJP

Respuesta

12

Use NIO con cada subproceso creando su propia asignación y leyendo los datos en su propio búfer privado. Mantenga el tamaño de búfer privado óptimo. El sistema operativo lee el archivo en su caché de archivos en páginas y las páginas se leen en los almacenamientos intermedios privados. Si las mismas regiones son leídas por múltiples subprocesos, los datos se leerán desde las mismas páginas en la memoria caché de archivos y se guardarán algunos ciclos de E/S de archivos. A continuación hay un pequeño diagrama para indicar esto. Espero que ayude a entender mejor.

memory mapped file io

Con referencia al diagrama de arriba, abajo es alguna explicación. Una región del archivo está asignada a la memoria. Crear una asignación es solo una marca lógica para decir que desea leer de una parte determinada de un archivo. Una vez que se crea la asignación, la región mapeada está lista para ser leída. Cuando comienza a leer, el sistema operativo busca los datos del archivo en sus páginas en la memoria caché de archivos. La región podría asignarse a una o más páginas. Ahora, lee las páginas en su propio búfer privado (varias páginas a la vez para optimizar). Algún otro hilo podría estar leyendo la misma región que el primero, por lo que también lee las mismas páginas en su búfer privado. Tenga en cuenta que esta vez la lectura ocurre desde la memoria caché de archivos sin fallas de página. Después de haber procesado su búfer privado, solicita leer más. Tenga en cuenta que está leyendo una porción de su mapeo en su buffer privado a la vez. Su archivo puede ser de 100 MB y puede asignar una porción de 10 MB a la memoria; y usted podría tener un buffer privado de 40 KB y leería 40 KB de 10 MB primero. Luego solicite los próximos 40 KB y así sucesivamente. El sistema operativo verifica si los datos que desea leer ya se encuentran en la memoria caché. De lo contrario, se produce un error de página y el sistema operativo obtiene los datos solicitados en las páginas. Nuevamente, estos datos pueden compartirse si se solicitan múltiples hilos para leer la misma región. Puede usar el caché de archivos para leer en lugar de crear su propio buffer privado. Sin embargo, esto puede provocar fallas múltiples en la página si el archivo se lee simultáneamente varias veces en varias regiones. Por lo tanto, en este caso, es mejor tener un búfer privado de tamaño óptimo.

+0

Hola Vikas, ¿podrías explicarlo con más detalle? Soy muy nuevo en NIO. –

+0

@Grace He puesto un diagrama para mostrar cómo funciona. Consulte el archivo mapeado en memoria io ejemplos disponibles en la web. – Drona

+0

Gracias por su explicación más detallada. En mi caso, tendré un archivo de aproximadamente 100M y aproximadamente 10000 clientes que necesitan leer todo el archivo. Entonces, a lo sumo necesitaré 10000 hilos, ¿cada hilo necesita un buffer privado como 100M? Me pregunto si el uso total de la memoria es demasiado alto. –

Cuestiones relacionadas