在并发方面我是个新手,在发现问题时我不确定自己,我正在查看一个相当成熟的代码库,发现以下代码(为简洁而编辑),我认为这些代码容易受到数据竞争的影响:
public class Example extends Thread {
boolean condition = false;
public void run () {
while (true) {
synchronized (this) {
try {
while( condition ) wait();
}
catch (InterruptedException e) { /*for brevity*/ }
}
// non-blocking computation
}
}
public void setTrue () { condition = true; }
public void setFalse () {
synchronized (this) {
condition = false;
this.notifyAll();
}
}
}
据我了解condition
必须是易失性的,因为即使使用同步块,编译器也不会发出任何内存屏障;如果它是编译器中的易失性存储,condition
则会setTrue
发出StoreEnter.
我是否可以相信上述内容容易受到数据竞争的影响?如果是这样,我如何通过一个例子来见证数据竞赛(而不是简单地知道 JMM 提供的保证)。在循环中随机调用线程的简单测试setTrue
不会发现数据竞争。
另外,我认为在这里使用 notifyAll 有点过分,因为要检查一个条件并且只有一个线程会等待它,对吗?
谢谢你。