Как я там уже где-то писал в комментариях, теория не работает потому, что нужно выставлять барьер между инициализацией класса и "публикацией" ссылки класса "наружу". Потому что, де факто инициализация может случиться позже присваивания. Из-за пресловутого operation reordering. И тогда первый тред, который еще не зашел в синхронизированный блок, может увидеть не NULL ссылку на недостроенный объект и начать работать с ним. В плюсах будет точно такая же фигня. Volatile в java, насколько я понимаю, делает этот самый memory barrier на кажду операцию доступа к volatile переменной. Таким образом, проверка if (worker == NULL) вне synchronized перестает, наверное, "облегченной". Вот тут, например, (http://blogs.msdn.com/brada/archive/2004/05/12/130935.aspx) говорят, что лучше не использовать volatile, а явным образом использовать memory barrier. В частности, это всегда корректно даже при отложенной инициализации.
no subject
Date: 2007-04-12 08:00 pm (UTC)Volatile в java, насколько я понимаю, делает этот самый memory barrier на кажду операцию доступа к volatile переменной. Таким образом, проверка
if (worker == NULL)
вне synchronized перестает, наверное, "облегченной". Вот тут, например, (http://blogs.msdn.com/brada/archive/2004/05/12/130935.aspx) говорят, что лучше не использовать volatile, а явным образом использовать memory barrier. В частности, это всегда корректно даже при отложенной инициализации.