Является ли это лучшей версией двойной проверки блокировки без энергозависимости и синхронизации?

Ниже приведен фрагмент кода от эффективной блокировки Java 2-й редакции с двойной проверкой

// Двойная проверка идиомы для ленивой инициализации полей экземпляра

private volatile FieldType field;

FieldType getField() {
    FieldType result = field;
    if (result == null) {  // First check (no locking)
        synchronized(this) {
            result = field;
            if (result == null)// Second check (with locking)  
                field = result = computeFieldValue();
        }
    }
    return result;
}

Из того, что я знаю, главная проблема с двойной проверкой блокировки - это переупорядочение внутри второй проверки блокировки, чтобы другой поток мог видеть значения поля / результата в виде набора, которые могут быть неэффективными при выполнении. Чтобы избежать этого, мы делаем ссылку на поле как изменчивую, чтобы гарантировать видимость и переупорядочение.

Но это может быть достигнуто с помощью приведенного ниже кода также

private FieldType field; // non volatile
private volatile boolean fence = false;

FieldType getField() {
    if (field == null) {  // First check (no locking) // no volatile read
        synchronized(this) {   //  inside synch block no problem of visibilty will latest           //value  of field 
            if (field == null) {// Second check (with locking)  
                Object obj =  computeFieldValue();
             fence = true; // any volatile write will take. this will make sure statements are //not reorder with setting field as non null.
            field = (FieldType)obj; // this will be only set after computeFieldValue has been //completed fully
           }
        }
    }
    return field;
}

Таким образом, после того, как инициализация будет выполнена, никакой поток не будет нуждаться в энергозависимом чтении или накладных расходах синхронизации. Пожалуйста, посмотрите, правильны ли мои предположения или нет?

Ответы на вопрос(3)

Ваш ответ на вопрос