0

我已经知道,如果我从另一个线程写入非易失性字段,他可能会缓存它,这样所有其他线程都不会看到实际值。但是,如果我在线程对象上调用例如start()AFTER 分配值到归档,JVM 将为所有其他线程更新这个值。但是,如果我将执行相同的操作但不直接将值分配给字段,JVM 会更新该字段的值,如下所示:object.field = 100但使用调用方法object.setFiled(100)

public class Main {
int value;

public static void main(String[] args) {
    Main main = new Main();
    main.value = 100;
    new Thread(() -> System.out.println(main.getValue())).start();
    

在这种情况下,所有其他线程的字段值肯定是相同的

}

public int getValue() {
    return value;
}
}

public class Main {
private int value;

public static void main(String[] args) {
    Main main = new Main();
    main.setValue(100);
    new Thread(() -> System.out.println(main.getValue())).start();

但是在这种情况下结果会一样吗?

}

public int getValue() {
    return value;
}

public void setValue(int value) {
    this.value = value;
}
}
4

1 回答 1

1

在这种情况下,如何在线程中更新某些内容的机制(无论是直接字段访问还是通过设置器)都无关紧要。JLS 17.4.5 声明“对线程的 start() 调用发生在已启动线程中的任何操作之前。” 在单个线程中“如果 x 和 y 是同一个线程的操作,并且 x 在程序顺序中位于 y 之前,则 [x 在 y 之前发生]”。在这种情况下,使值对原始线程可见的方法设置器或字段分配也会使该值对新启动的线程可见。粗略地说,在调用 start() 时调用 start() 的线程可见的任何内容对新线程同样可见,只要正在查看的对象没有发生变化并且查看状态的尝试没有发生变化东西(例如。

于 2020-12-20T16:50:45.397 回答