什么" volatile写语义"意思?

时间:2018-06-05 20:20:36

标签: java concurrency volatile

如果我们在set方法中省略setArray会发生什么?

你是否可以编写代码,甚至使用一些辅助信号量,这会显示使用这个易失性写入和调用setArray的必要条件?

下面的代码来自CopyOnWriteArrayList.java

final transient Object lock = new Object();    
private transient volatile Object[] array;
public CopyOnWriteArrayList() { setArray(new Object[0]); }

public E set(int index, E element) {
    synchronized (lock) {
        Object[] elements = getArray();
        E oldValue = elementAt(elements, index);

        if (oldValue != element) {
            int len = elements.length;
            Object[] newElements = Arrays.copyOf(elements, len);
            newElements[index] = element;
            setArray(newElements);
        } else {
            // Not quite a no-op; ensures volatile write semantics
            setArray(elements);  // <------ what is it actually for ? ------
                                 // what If it would me ommited ?
        }
        return oldValue;
    }
}    

final void setArray(Object[] a) {
    array = a;
}

1 个答案:

答案 0 :(得分:0)

&#34;易失性写&#34;语义在这里意味着将安全发布新数组。您可能会注意到,有一种方法

final Object[] getArray() {
    return array;
}

这意味着您可以在没有任何同步的情况下读取已发布的数组(这是CopyOnWriteArrayList的重点)。如果在java中有可能同时读取和写入对象,则 要使用volatile关键字。否则,对象可能会不一致地发布。如果以这种方式发布对象,则可能无法正确初始化其某些字段。

有关主题的过多信息,建议您阅读this great article