He intentado que funcione lo que creo que es la forma más simple posible de subprocesamiento en mi aplicación, pero simplemente no puedo hacerlo.C# Threading - Lectura y hash de múltiples archivos al mismo tiempo, ¿método más fácil?
Lo que quiero hacer: tengo un formulario principal con una barra de estado y una barra de progreso. Tengo que leer algo entre 3 y 99 archivos y agregar sus hashes a una cadena [] que quiero agregar a una lista de todos los archivos con sus hashes respectivos. Luego tengo que comparar los elementos de esa lista con una base de datos (que viene en archivos de texto). Una vez hecho todo esto, tengo que actualizar un cuadro de texto en el formulario principal y la barra de progreso al 33%; sobre todo, simplemente no quiero que la forma principal se congele durante el procesamiento.
Los archivos con los que trabajo siempre suman 1.2GB (+/- unos pocos MB), lo que significa que debería poder leerlos en bytes [] sy procesarlos desde allí (tengo que calcular CRC32 , MD5 y SHA1 de cada uno de esos archivos, por lo que debería ser más rápido que leerlos todos desde un HDD 3 veces).
También debo tener en cuenta que algunos archivos pueden ser de 1 MB mientras que otro puede ser de 1 GB. Inicialmente, quería crear 99 hilos para 99 archivos, pero parece no ser el mejor, supongo que sería mejor reutilizar los hilos de los archivos pequeños, mientras que los hilos de los archivos aún se están ejecutando. Pero eso me suena bastante complicado, así que no estoy seguro de que sea sabio tampoco.
Hasta ahora he probado workerThreads y backgroundworkers, pero ninguno parece funcionar demasiado bien para mí; al menos los backgroundWorkers funcionaron ALGUNAS veces, pero ni siquiera puedo entender por qué no lo harían las otras veces ... de cualquier manera la forma principal aún se congeló. Ahora que he leído sobre la Biblioteca de tareas paralelas en .NET 4.0, pero pensé que debería preguntarle a alguien que sabe lo que está haciendo antes de perder más tiempo en esto.
Lo que quiero hacer se ve algo como esto (sin enhebrar):
List<string[]> fileSpecifics = new List<string[]>();
int fileMaxNumber = 42; // something between 3 and 99, depending on file set
for (int i = 1; i <= fileMaxNumber; i++)
{
string fileName = "C:\\path\\to\\file" + i.ToString("D2") + ".ext"; // file01.ext - file99.ext
string fileSize = new FileInfo(fileName).Length.ToString();
byte[] file = File.ReadAllBytes(fileName);
// hash calculations (using SHA1CryptoServiceProvider() etc., no problems with that so I'll spare you that, return strings)
file = null; // I didn't yet check if this made any actual difference but I figured it couldn't hurt
fileSpecifics.Add(new string[] { fileName, fileSize, fileCRC, fileMD5, fileSHA1 });
}
// look for files in text database mentioned above, i.e. first check for "file bundles" with the same amount of files I have here; then compare file sizes, then hashes
// again, no problems with that so I'll spare you that; the database text files are pretty small so parsing them doesn't need to be done in an extra thread.
qué alguien ser tan amable de apuntar en la dirección correcta? Estoy buscando la forma más fácil de leer y copiar esos archivos rápidamente (creo que el hash toma algún tiempo en el que otros archivos ya puedan leerse) y guardar el resultado en una cadena [], sin congelar la forma principal, nada más , nada menos.
Estoy agradecido por cualquier entrada.
EDITAR para aclarar: por "backgroundWorkers working some of time" Quise decir que (para el mismo conjunto de archivos), tal vez la primera y cuarta ejecución de mi código produce la salida correcta y la UI se descongela en 5 segundos para la segunda, tercera y quinta ejecución congela el formulario (y después de 60 segundos recibo un mensaje de error que dice que un hilo no respondió dentro de ese marco de tiempo) y tengo que detener la ejecución a través de VS.
Gracias por todas sus sugerencias y sugerencias, ya que todos han adivinado correctamente que soy completamente nuevo para enhebrar y tendré que leer en los excelentes enlaces que publicaron. Luego probaré esos métodos y marcaré la respuesta que más me ayudó. ¡Gracias de nuevo!
¿Qué quiere decir por el BackgroundWorker trabajando parte del tiempo? Si se implementa correctamente, el procesamiento realizado en BackgroundWorker no debe provocar que el formulario se congele. – evasilchenko
Si están en 1 disco, solo necesita 1 (extra) subproceso. –
Este artículo puede ser de ayuda para usted: http://www.hanselman.com/blog/BackToParallelBasicsDontBlockYourThreadsMakeAsyncIOWorkForYou.aspx –