当只有两个线程的时候,程序加减交替执行,运行正常,当有四个线程的时候,程序可能出现连加连减的情况。请帮忙看看问题出在哪里。详细代码如下:
public class NumDemo {
public static void main(String[] args) {
Resource res = new Resource();
Runnable ars =new AddThread(res);
Runnable srs = new SubThread(res);
new Thread(ars,"加法A").start();
new Thread(ars,"加法B").start();
new Thread(srs,"减法X").start();
new Thread(srs,"减法Y").start();
}
}
class Resource{
private int num =0 ;
//定义执行数字加减的标记,当flag = true时,执行加法,否则执行减法
private boolean flag = true;
public void add() {
synchronized (this){
if(!this.flag){
System.out.println(Thread.currentThread()
.getName()
+" 等待中" +this.flag);
try {
super.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
try {
Thread.sleep(200);
} catch (InterruptedException e) {
e.printStackTrace();
}
//执行完成加法以后,将flag标记设置为false,
this.flag=false;
this.num++;
System.out.println(Thread.currentThread()
.getName()
+" current number =" +this.num+" "+this.flag);
super.notifyAll();//唤醒其他等待的线程
}
}
public void sub(){
synchronized (this){
if(this.flag==true){
System.out.println(Thread.currentThread()
.getName()
+" 等待中" +this.flag);
try {
super.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
this.flag=true;
this.num--;
System.out.println(Thread.currentThread()
.getName()
+" current number =" +this.num +" "+this.flag);
super.notifyAll();
}
}
}
class AddThread implements Runnable{
private Resource res;
public AddThread(Resource res){
this.res = res;
}
@Override
public void run() {
for(int i=0;i<50;i++){
try {
this.res.add();
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
class SubThread implements Runnable{
private Resource res;
public SubThread(Resource res){
this.res = res;
}
@Override
public void run() {
for(int i=0;i<50;i++){
try {
this.res.sub();
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
出现问题的原因为:Thread.sleep()会发生切换,因此需要再执行更新操作时,重新判定标记是否已经更新。
版权声明:本文内容由阿里云实名注册用户自发贡献,版权归原作者所有,阿里云开发者社区不拥有其著作权,亦不承担相应法律责任。具体规则请查看《阿里云开发者社区用户服务协议》和《阿里云开发者社区知识产权保护指引》。如果您发现本社区中有涉嫌抄袭的内容,填写侵权投诉表单进行举报,一经查实,本社区将立刻删除涉嫌侵权内容。