gpt4 book ai didi

java - 为什么变量在没有同步的情况下对其他线程可见?

转载 作者:行者123 更新时间:2023-12-03 13:08:42 24 4
gpt4 key购买 nike

这个问题在这里已经有了答案:





Loop doesn't see value changed by other thread without a print statement

(1 个回答)


4年前关闭。




我有关于内存可见性的理论问题。这是示例代码:

public class TwoThreadApp {

private static class A {
int x = 1;
}

public static void main(String[] arg) throws InterruptedException {
A a = new A();

Thread t2 = new Thread(() -> {
while (true) {
if (a.x == 2) {
System.out.println(a.x);
return;
}
// IO operation which makes a.x visible to thread "t2"
System.out.println("in loop");
}
});

t2.start();
Thread.sleep(100);
a.x = 2;
}
}
  • 没有 System.out.println("in loop")程序无限期地工作,这是预期的行为。
  • 但与 System.out.println("in loop")它总是完成,这是意料之外的,因为 a.x 不是 volatile 的并且没有同步块(synchronized block)。

  • 我的环境:ubuntu 16.04,openjdk 1.8.0_131

    为什么它会这样?

    最佳答案

    Without System.out.println("in loop") programs works indefinitely, which is expected behavior.



    相反,程序应该退出。程序继续运行,这是 x 的副作用。被缓存(作为非 volatile )。缓存是编译器的优化,你不应该依赖它(取决于 JVM 设置)。

    But with System.out.println("in loop") it is always completes, which is not expected, because a.x is not volatile and there is no synchronized blocks.



    这是恕我直言的预期行为。我不能告诉你为什么,我假设 IO 操作涉及清除线程缓存(如果有人有更好的洞察力,请评论/更正)。

    在没有同步或锁的情况下访问变量或在多个线程中 volatile 可能真的是不可预测的。

    您甚至可以使用 -Djava.compiler=NONE 禁用许多优化。 (那么程序应该总是按预期退出)

    关于java - 为什么变量在没有同步的情况下对其他线程可见?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47030587/

    24 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com