简体   繁体   English

是否保证在另一个线程中看到一个线程中的非易失性成员变量的赋值?

[英]Are assignments to non-volatile member variables in one thread guaranteed to be seen in another thread?

Consider the Java example below. 考虑下面的Java示例。 Notice that neither of the class member variables are declared to be volatile . 请注意,这两个类成员变量都没有声明为volatile If I am understanding the memory model and "happens before" rules correctly, a Java implementation could optimize the run() method so that it runs forever, even if another thread calls the stopNow() method. 如果我正在理解内存模型并且“之前发生”规则正确,Java实现可以优化run()方法,以便它永远运行,即使另一个线程调用stopNow()方法。 This can happen because there is nothing in the run() method that forces the thread to read the value of stop more than once. 这可能发生,因为run()方法中没有任何内容强制线程多次读取stop的值。 Is that correct? 那是对的吗? If not, why not? 如果没有,为什么不呢?

class Example implements Runnable {
    boolean stop = false;
    int value = 0;

    public void stopNow() {
       stop = true;
    }

    public int getValue() {
        return value;
    }

    @Override
    public void run() {
        // Loop until stop is set to true.
        while (!stop) {
            ++value;
        }
        return;
    }
}

that can be modified by another thread but this is not gurranteed. 可以被另一个线程修改,但这不是gurranteed。 also this is not thread safe either. 这也不是线程安全的。 To make a variable gurranteed to see from another thread you need to do any of the following 要使变量gurranteed从另一个线程中看到,您需要执行以下任何操作

Changes to fields made by one thread are guaranteed to be visible to other threads only under the following conditions: 只有在以下条件下,才能保证一个线程对字段的更改对其他线程可见:

  • A writing thread releases a synchronization lock and a reading thread subsequently acquires that same synchronization lock. 写入线程释放同步锁,读取线程随后获取相同的同步锁。
  • If a field is declared as volatile, any value written to it is flushed and made visible by the writer thread before the writer 如果一个字段被声明为volatile,那么写入它的任何值都会被写入之前的写入器线程刷新并使其可见
    thread performs any further memory operation (ie, for the purposes 线程执行任何进一步的内存操作(即,用于此目的
    at hand it is flushed immediately). 在手边它立即被冲洗)。 Reader threads must reload the 读者线程必须重新加载
    values of volatile fields upon each access. 每次访问时的volatile字段的值。
  • The first time a thread accesses a field of an object, it sees either the initial value of the field or a value since written by some other thread. 线程第一次访问对象的字段时,它会看到字段的初始值或自某个其他线程写入的值。
  • As a thread terminates, all written variables are flushed to main memory. 当一个线程终止时,所有写入的变量都被刷新到主存储器。 For example, if one thread synchronizes on the termination of another thread using Thread.join, then it is guaranteed to see the 例如,如果一个线程使用Thread.join在另一个线程的终止上同步,则保证看到
    effects made by that thread (see §4.3.2). 该线程产生的影响(见§4.3.2)。

helpful SO thread 有用的SO线程

That's correct. 那是对的。 That's one of the reasons you might want to use volatile . 这是您可能想要使用volatile的原因之一。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 同步保证线程是否会看到另一个线程修改的非易失性变量的最新值? - Does synchronized guarantee a thread will see the latest value of a non-volatile variable being modified by another thread? 由该类的方法延迟分配的非易失性变量不能被另一个线程读取吗? - Can a non-volatile variable that is delayed assigned to by a method of the class not be read by another thread? 非易失性字段+来自另一个线程的第一个对象访问(java) - Non-volatile fields + first object access from another thread (java) 是否可以修改非易失性变量,以便另一个线程能够“看到”更新? - Is it possible to modify a non-volatile variable such that another thread is able to “see” the update? 在从另一个线程读取期间是否可以读取非易失性变量的陈旧值? - Is it possible to read stale value of non-volatile variable during read from another thread? 对非易失性字段的同步访问是否安全? - Is synchronized access to non-volatile fields thread safe? 具有非易失性布尔变量的 Thread.sleep 行为 - Thread.sleep behaviour with non-volatile boolean variable 为什么对非易失性的写入对主线程可见? - Why is the write to non-volatile visible to the main-thread? volatile 会影响非易失性变量吗? - Does volatile influence non-volatile variables? 是否保证非易失性 var 的顺序线程运行的可见性? - Is visibility guaranteed for sequential thread runs for non volatile var?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM