thread studio problem loop current java multithreading sleep wait

java - studio - Implementacion de Thread.sleep()



thread sleep java problem (3)

Hoy tuve una entrevista en la que le hice al candidato una pregunta bastante habitual y básica sobre la diferencia entre Thread.sleep() y Object.wait() . Esperaba que respondiera algo como esto , pero dijo que estos métodos son básicamente lo mismo, y lo más probable es que Thread.sleep esté usando Object.wait() dentro de él, pero el sleep sí mismo no requiere bloqueo externo. Esta no es exactamente una respuesta correcta, porque en JDK 1.6 este método tiene la siguiente firma.

public static native void sleep(long millis) throws InterruptedException;

Pero mi segundo pensamiento fue que no es tan ridículo. Es posible usar la espera programada para lograr el mismo efecto. Echa un vistazo al siguiente fragmento de código:

public class Thread implements Runnable { private final Object sleepLock = new Object(); // other implementation details are skipped public static void sleep(long millis) throws InterruptedException { synchronized (getCurrentThread().sleepLock){ getCurrentThread().sleepLock.wait(millis); } }

En este caso, sleepLock es un objeto que se usa particularmente para el bloque de sincronización dentro del método de sleep . Supongo que los ingenieros de Sun / Oracle son conscientes de la afeitadora de Occam, por lo que el sleep tiene una implementación nativa a propósito, por lo que mi pregunta es por qué utiliza las llamadas nativas.

La única idea que se me ocurrió fue suponer que alguien podría encontrar una invocación útil como Thread.sleep(0) . Tiene sentido para la gestión del programador de acuerdo con este artículo:

Esto tiene el efecto especial de borrar el cuanto del subproceso actual y ponerlo al final de la cola para su nivel de prioridad. En otras palabras, todos los subprocesos ejecutables de la misma prioridad (y los de mayor prioridad) tendrán la oportunidad de ejecutarse antes de que el subproceso asignado sea el siguiente tiempo de CPU dado.

Así que un bloque synchronized dará una sobrecarga innecesaria.

¿Conoce alguna otra razón para no usar la espera temporizada en la Thread.sleep() de Thread.sleep() ?


¿Conoce alguna otra razón para no usar la espera temporizada en la Thread.sleep() de Thread.sleep() ?

Debido a que las bibliotecas de subprocesos nativos proporcionan una función de suspensión perfectamente buena: http://www.gnu.org/software/libc/manual/html_node/Sleeping.html

Para comprender por qué los subprocesos nativos son importantes, comience en http://java.sun.com/docs/hotspot/threads/threads.html

La versión 1.1 se basa en hilos verdes y no se tratará aquí. Los subprocesos verdes son subprocesos simulados dentro de la VM y se usaron antes de ir a un modelo de subprocesos nativo del sistema operativo en 1.2 y más allá. Los subprocesos verdes pueden haber tenido una ventaja en Linux en un momento dado (ya que no tiene que generar un proceso para cada subproceso nativo), pero la tecnología de VM ha avanzado significativamente desde la versión 1.1 y cualquier beneficio que los subprocesos verdes hayan eliminado en el pasado El rendimiento aumenta con los años.


Thread.sleep () no se despertará temprano por activaciones espurias . Si usa Object.wait (), para hacerlo correctamente (es decir, asegúrese de esperar el tiempo suficiente) necesitará un bucle con una consulta para el tiempo transcurrido (como System.currentTimeMillis ()) para asegurarse de que espera lo suficiente.

Técnicamente, podrías lograr la misma funcionalidad de Thread.sleep () con Object.wait () pero necesitarías escribir más código para hacerlo correctamente.

Esta es también una discusión relevante y útil.


Uno podría decir fácilmente que la navaja de Occam corta en la otra dirección. Se asume que la implementación normal / esperada de JVM subyacente a JDK enlaza ''subprocesos'' de java en subprocesos nativos la mayor parte del tiempo, y poner un subproceso en suspensión es una función fundamental de la plataforma subyacente. ¿Por qué volver a implementarlo en java si el código de subprocesos va a ser nativo de todos modos? La solución más simple es usar la función que ya está allí.

Algunas otras consideraciones: la sincronización no cuestionable es despreciable en las JVM modernas, pero esto no siempre fue así. Solía ​​ser una operación bastante "costosa" para adquirir ese monitor de objeto.

Si implementa un hilo durmiente dentro del código java, y la forma en que lo implementa no se enlaza con un hilo nativo de espera, el sistema operativo tiene que seguir programando ese hilo para ejecutar el código que verifica si es hora de despertarse. Como se ha resumido en los comentarios, esto obviamente no sería cierto para su ejemplo en una JVM moderna, pero es difícil decir 1) lo que pudo haber estado en su lugar y esperado en el momento en que la clase Thread se especificó por primera vez de esa manera. y 2) Si esa afirmación funciona para todas las plataformas, es posible que alguna vez se haya querido implementar una JVM.