tiempo threads threading programacion multitarea mismo metodos manejo hilos entre eliminar ejecutar datos crear con compartir argumentos multithreading asynchronous

multithreading - threads - multitarea en python



¿Una llamada asincrónica siempre crea/llama un nuevo hilo? (6)

El modelo de Javascript es de subproceso único . Una llamada asincrónica no es un nuevo hilo, sino que interrumpe un hilo existente. Es análogo a las interrupciones en un kernel.

Sí, tiene sentido tener llamadas asincrónicas con un solo hilo. He aquí cómo pensarlo: cuando llama a una función dentro de un único hilo, el estado del método actual se inserta en una pila (es decir, variables locales). La subrutina se invoca y finalmente regresa, momento en el que el estado original se elimina de la pila.

¡Con una devolución de llamada asíncrona, sucede lo mismo! La diferencia es que el sistema invoca la subrutina, no el código actual que invoca una subrutina.

¿La llamada asincrónica siempre crea un nuevo hilo?

Ejemplo:

Si JavaScript tiene un solo subproceso, ¿cómo puede hacer una devolución de datos asincrónica? ¿Está realmente bloqueando hasta que reciba una devolución de llamada? Si es así, ¿se trata realmente de una llamada asincrónica?


En muchas aplicaciones de GUI, una llamada asincrónica (como invokeLater de Java) simplemente agrega el objeto Runnable a su cola de hilos de la GUI. El hilo de GUI ya está creado y no crea un nuevo hilo. Pero los hilos ni siquiera son estrictamente necesarios para un sistema asíncrono. Tomemos, por ejemplo, libevent, que usa select / poll / kqueue, etc. para hacer llamadas no bloqueadas a sockets, que luego activan devoluciones de llamada a su código, completamente sin hilos.


Esta es una pregunta interesante.

La programación asincrónica es un paradigma de programación que es principalmente de un solo hilo, es decir, "siguiendo un hilo de ejecución continua".

Se refiere a javascript, así que hablemos de ese idioma, en el entorno de un navegador web. Un navegador web ejecuta un único hilo de ejecución javascript en cada ventana, maneja eventos (como onclick = "someFunction ()") y conexiones de red (como llamadas xmlhttprequest).

<script> function performRequest() { xmlhttp.open("GET", "someurl", true); xmlhttp.onreadystatechange = function() { if (xmlhttp.readyState == 4) { alert(xmlhttp.responseText); } } xmlhttp.send(sometext); } </script> <span onclick="performRequest()">perform request</span>

(Este es un ejemplo que no funciona, solo para la demostración de conceptos).

Para hacer todo de una manera asincrónica, el hilo de control tiene lo que se conoce como un "bucle principal". Un ciclo principal se ve así:

while (true) { event = nextEvent(all_event_sources); handler = findEventHandler(event); handler(event); }

Es importante tener en cuenta que este no es un "bucle ocupado". Esto es como un hilo de dormir, esperando que ocurra la actividad. La actividad podría ser ingresada por el usuario (movimiento del mouse, un clic de botón, escritura) o podría ser una actividad de red (la respuesta del servidor).

Entonces en el ejemplo de arriba,

  1. Cuando el usuario hace clic en el tramo, se generará un evento ButtonClicked, findEventHandler () buscará el evento onclick en la etiqueta span, y luego se llamará ese controlador con el evento.
  2. Cuando se crea la solicitud xmlhttp, se agrega a la lista all_event_sources de orígenes de eventos.
  3. Después de que la función performRequest () retorna, el mainloop está esperando en el paso nextEvent () esperando una respuesta. En este punto, no hay nada que bloquee el manejo de otros eventos.
  4. Los datos vuelven del servidor remoto, nextEvent () devuelve el evento de red, se encuentra que el controlador de eventos es el método onreadystatechange (), se llama ese método y se activa un diálogo de alerta ().

Vale la pena señalar que alert () es un diálogo de bloqueo. Mientras ese diálogo está activo, no se pueden procesar más eventos. Es una excentricidad del modelo de páginas web javascript que tenemos un método disponible que bloqueará la ejecución posterior dentro del contexto de esa página.


No sé sobre javascript, pero por ejemplo en el mundo de Windows Forms, las invocaciones asincrónicas se pueden realizar sin múltiples hilos. Esto tiene que ver con la forma en que funciona Windows Message Pump. Básicamente, una aplicación de Windows Forms configura una cola de mensajes a través de la cual Windows coloca mensajes notificándolo sobre eventos. Por ejemplo, si mueve el mouse, los mensajes se colocarán en esa cola. La aplicación Windows Forms estará en un bucle sin fin que consumirá todos los mensajes que se le envíen. De acuerdo con lo que contenga cada mensaje, moverá las ventanas, las volverá a pintar o incluso invocará métodos definidos por el usuario, entre otras cosas. Los delegados identifican las llamadas a los métodos. Cuando la aplicación encuentra una instancia de delegado en la cola, felizmente invoca el método al que hace referencia el delegado.

Por lo tanto, si se encuentra en un método haciendo algo y desea generar un trabajo asincrónico sin crear un nuevo hilo, todo lo que tiene que hacer es colocar una instancia delegada en la cola, utilizando el método Control.BeginInvoke. Ahora, esto no es en realidad multiproceso, pero si arrojas pequeñas piezas de trabajo a la cola, se verá como multiproceso. Si, por otro lado, le da un método lento para ejecutar, la aplicación se congelará hasta que se complete el método, que se verá como una aplicación atascada, aunque esté haciendo algo.


No, pero más de un hilo estará involucrado.

Una llamada asincrónica podría iniciar otro hilo para hacer el trabajo, o podría publicar un mensaje en una cola en otro hilo que ya esté ejecutándose. La persona que llama continúa y el llamado vuelve a llamar una vez que procesa el mensaje.

Si desea hacer una llamada sincrónica en este contexto, deberá publicar un mensaje y esperar activamente a que se realice la devolución de llamada.

Entonces, en resumen: más de un hilo estará involucrado, pero no necesariamente crea un nuevo hilo.


Un par de notas sobre JavaScript en particular:

XMLHttpRequest s no son bloqueantes por defecto. El método send() regresa inmediatamente después de que la solicitud ha sido retransmitida a la pila de red subyacente. Una respuesta del servidor programará una invocación de su devolución de llamada en el ciclo de eventos como se discutió en las otras respuestas excelentes.

Esto no requiere un nuevo hilo. La API de socket subyacente es seleccionable, similar a java.nio.channels en Java.

Es posible construir objetos síncronos XMLHttpRequest pasando false como el tercer parámetro para open() . Esto hará que el método send() se bloquee hasta que se reciba una respuesta del servidor, colocando así el bucle de eventos a merced de la latencia de la red y posiblemente colgando el navegador hasta el tiempo de espera de la red. Esto es un Bad Thing ™.

Firefox 3.5 introducirá el HTML multiproceso de honesto a dios con la clase Worker . El código de fondo se ejecuta en un entorno completamente separado y se comunica con la ventana del navegador mediante la programación de devoluciones de llamada en el bucle de evento.