public class Test {
int counter = 1;
Object lock = new Object();
public Runnable A = new Runnable() {
@Override
public void run() {
synchronized (lock) {
if (counter % 2 == 0) {
try {
System.out.println("counter 是偶数:" + counter);
Thread.sleep(100);
counter++;
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
};
}
使用if判断一个可能会被其它线程修改的值,是不安全的。可能会出现虚假唤醒。因为线程无法监听状态的改变。可能当前线程判断通过了,但下一秒CPU切换到其它线程,而且又改变了状态值,那么在切换会这个线程时它就不知道监听状态已经改变了。
public class Test {
int counter = 1;
Object lock = new Object();
public Runnable A = new Runnable() {
@Override
public void run() {
synchronized (lock) {
while (counter % 2 == 0) {
try {
System.out.println("counter 是偶数:" + counter);
Thread.sleep(100);
counter++;
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
};
}
这样的代码是怎样执行的呢。首先需要获取到锁,才能执行while循环,在这个时候条件不满足它就会一直循环。等到了条件满足就执行任务,然后再释放锁。即使执行过程中被CPU切换了线程,那么在线程恢复时将会重新判断条件值,这样就可以保证条件值的有效性。