windows - ¿Por qué está intentando abrir un TOpenDialog generando una tonelada de hilos?
multithreading delphi (1)
Tengo un formulario muy simple con un TOpenDialog y un botón. Cuando presiono el botón, se llama Ejecutar en el diálogo. Si observo en el depurador, el hecho de abrir el cuadro de diálogo genera algo así como 14 hilos, y tampoco desaparecen cuando cierro el cuadro de diálogo.
¿Alguien tiene alguna idea de lo que está pasando con eso?
Imagina que quieres mostrar a tus amigos lo hermoso que es el noroeste del Pacífico. Decides emprender un viaje para tomar algunas fotos de la puesta de sol sobre el Pacífico . Lo que realmente te importa son los archivos de imagen que se dirigen a casa, donde se pueden cargar en Facebook. En realidad, la cámara, las lentes y el trípode deben ser transportados durante los Olympics y de vuelta. También debe traer al fotógrafo (usted mismo) que configurará la cámara y presionará el disparador. El fotógrafo debe moverse hacia atrás y hacia atrás con relativa comodidad, de modo que tome asiento en el que el fotógrafo descansará mientras realiza el viaje. Este asiento está encerrado en una caja de metal brillante con un montón de otras piezas de metal, vidrio y goma, algunas de las cuales están girando y en movimiento recíproco. Al final, alrededor de dos toneladas de material (y un ser humano vivo) realiza un viaje de varias horas, quemando galones de líquido de hidrocarburos, con el objetivo de transferir algunos datos de la costa a Internet.
Exactamente lo mismo sucede con su aplicación. Cuando el usuario desea abrir un archivo utilizando el cuadro de diálogo "Abrir archivo", el usuario espera poder:
- navegue hasta el directorio que contiene el archivo (El directorio puede estar en el disco duro local o en un CD / DVD / BR o en una unidad de red o archivo, etc. Los medios pueden estar encriptados o comprimidos, lo que debe mostrarse de manera diferente. Es posible que los medios no estén enchufado, para lo que es posible que se solicite al usuario. Es posible que los medios requieran las credenciales del usuario, que deben solicitarse);
- conéctese a un nuevo directorio usando su URI / UNC (mapee la unidad);
- buscar en el directorio para algunas palabras clave;
- copiar / borrar / renombrar algunos archivos;
- ver la lista de los archivos en ese directorio;
- vista previa del contenido de cada archivo en el directorio;
- seleccione el archivo que desea abrir;
- cambia de opinión y decide no abrir el archivo;
- hacer muchas otras cosas relacionadas con archivos.
El sistema operativo permite que todo esto suceda al darle a su proceso la mayor parte de la funcionalidad del Explorador de Windows. Y algo de esto tiene que suceder en segundo plano, de lo contrario los usuarios se quejarán de cuán insensible es el diálogo Abrir archivo. La forma obvia de ejecutar algunas tareas en segundo plano es ejecutarlas en diferentes subprocesos. Así que eso es lo que vemos.
¿Qué hay de los hilos dejados atrás, preguntas? Bueno, algunos de ellos se quedan allí en caso de que el usuario decida abrir otro archivo: ahorra mucho tiempo, tráfico y escritura en este caso. ¿Esa autenticación personalizada utilizada para este proceso en particular la última vez? - almacenado. ¿Los iconos de vista previa para esos PDF molestos? -- aún allí. ¿La longitud y la tasa de bits para cada película en el directorio? - Todavía disponible, no es necesario volver a analizarlos.
Por supuesto, los hilos no solo aparecían mágicamente por sí mismos. Echa un vistazo a cuántas DLL se han asignado en el proceso. Al observar algunos de ellos, se puede obtener una imagen bastante interesante de la funcionalidad que se ha agregado.
Otra forma interesante de verlo sería deshacerse de las pilas de llamadas en el momento en que se crea cada hilo. Esto muestra qué DLL (ya veces qué objeto) los creó. Así Here''s como un Win7 x64 crea todos los hilos. Uno puede encontrar el hilo del marco del Explorador que se está creando; alguna actividad OLE que se utilizará para crear una instancia de los filtros de archivos, algunos de los cuales pueden generar iconos de vista previa, superposiciones y información sobre herramientas; pocos hilos pertenecientes al subsistema de búsqueda; el enumerador de dispositivos de la shell (de modo que si el usuario conecta un nuevo dispositivo, aparecerá automáticamente en el cuadro de diálogo abierto); monitor de red de shell (ídem) y otras cosas.
La buena noticia es que sucede rápidamente y no agrega demasiados gastos generales a su proceso. La mayoría de los subprocesos pasan la mayor parte del tiempo esperando algunos eventos (como la memoria USB conectada), por lo que la CPU no pasa ningún tiempo ejecutándolos. Cada hilo consume 1 MB de espacio de direcciones virtuales en su proceso, pero solo unas pocas páginas de 4 KB de memoria física real. Y la mayoría, si no todas esas DLL, no usaron ningún ancho de banda de disco para cargarse: ya estaban en la RAM, por lo que solo se asignaron a su proceso de forma casi gratuita.
Al final, el usuario obtuvo una gran cantidad de funcionalidades útiles en una interfaz de usuario ágil, mientras que el proceso tuvo que hacer muy poco para lograr todo eso.