Java IO在线程变量共享上实现

时间:2017-03-28 14:22:59

标签: java multithreading

我对这样的代码段感到困惑:

public class LearnTest {

private static boolean tag = true;
private static int i = 0;

public static void main(String[] args) {

    new Thread(new Runnable() {
        @Override
        public void run() {
            while (tag) {
                //System.out.println("ok");
                i++;
            }
        }
    }).start();

    try {
        Thread.sleep(1000);
    }catch (Exception e) {
        e.printStackTrace();
    }

    tag = false;
    System.out.println(i);
  }
}

在代码中,我们有new-threadmain-thread。此代码的结果将是i的随机值,而new-thread将不会退出。因为new-thread不会获得新的tag值。

如果我们更改将使用tag修饰的volatile的定义,则会打印一些i的值,new-thread将退出。因为volatile会保持所有主题的可见性。

但是,当我为评论的代码行添加注释时,tag将不会被装饰为volatile,它会打印一些“ok”并退出。

为什么?

我认为Java的IO会执行synchronized之类的操作,它会强制tag的{​​{1}}边值从主共享内存中刷新。

这是正确的吗?

1 个答案:

答案 0 :(得分:0)

如果没有volatile,则线程不会保证以查看对值的更改。 可以看到它们。

在这种情况下,在从缓存中删除的值中添加System.out.println()结果(显然),因此它在某个时刻从主内存中获取。如果没有println(),则值保留在缓存中,并且您将获得无限(或至少非常长)的循环。

这是并发编程的一个难点,有时代码可能出现才能正常工作,但是无法确定总是是否正常工作。