public class Lazy {
private static boolean initialized = false;
static {
Thread thread = new Thread(
new Runnable {
public void run() {
initialized = true;
}
}
);
thread.start();
try {
thread.join();
} catch (InterruptedException ie) {
throw new AssertionError(ie);
}
}
public static void main(String[] args) {
System.out.println(initialized);
}
}
Кажется, что программа должна каждый раз печатать true, но нет! Она просто виснет.
Симпатичный deadlock. Попробую объяснить.
Понятно, что при обращении к методу
main
JVM начинает инициализировать класс. И только когда инициализация закончится будет вызван метод main
. Во время инициализации запускается метод run
. Однако, этот метод перед установкой initialized
в true
делает тоже проверку на то, что класс уже проинициализирован. Таким образом получается, что основной поток ждёт завершения фонового потока для завершения инициализации, а фоновый поток ждёт завершения инициализации. Вуаля!
Комментариев нет:
Отправить комментарий