论坛首页 Java企业应用论坛

java 多线程 生产者-消费问题

浏览 6618 次
精华帖 (0) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
作者 正文
   发表时间:2014-06-24  
最新在学习多线程,下午研究下了消费者-生产者问题,但是发现了问题,就是第一轮执行完毕后,无法继续执行了,各位大神求教育!
代码如下:

产品类
//产品类
public class Product {
	
	private String productName;
	
	private int productNum;
	
	private int maxNum = 100;

	public String getProductName() {
		return productName;
	}

	public void setProductName(String productName) {
		this.productName = productName;
	}

	public int getProductNum() {
		return productNum;
	}

	public void setProductNum(int productNum) {
		this.productNum = productNum;
	}

	public int getMaxNum() {
		return maxNum;
	}

	public void setMaxNum(int maxNum) {
		this.maxNum = maxNum;
	}
	
	
	
}


生产者类
//生产者
public class Producer implements Runnable{
	
	public Product pro = null;
	public String  user = null;
	public Producer(Product pro,String user){
		this.pro = pro;
		this.user = user;
	}
	
	public void run() {
		while(true){
			synchronized (this) {
				if(pro.getProductNum() >= 20){
					try {
						System.out.println("仓库已满...");
						wait();
					} catch (InterruptedException e) {
						e.printStackTrace();
					}
				}else{
					pro.setProductNum(pro.getProductNum()+1);
					System.out.println("生产了产品:  "+pro.getProductNum());
				}
			}
		}
		
	}
	
	
	
}


消费者类:
//消费者
public class Consumer implements Runnable{

	public Product pro = null;
	public String  user = null;
	public Consumer(Product pro,String user){
		this.pro = pro;
		this.user = user;
	}
	
	public void run() {
		while(true){
			synchronized (this) {
				if(pro.getProductNum() > 0){
					System.out.println("消费了产品:  "+pro.getProductNum());
					pro.setProductNum(pro.getProductNum()-1);
				}else{
					try {
						System.out.println("仓库已空...");
						wait();
					} catch (InterruptedException e) {
						e.printStackTrace();
					}
				}
			}
		}
	}
	
	
}


测试类
public class producerConsumerTest {
	
	public static void main(String[] args) {
		Product pro = new Product(); 
        Producer producer = new Producer(pro, "生产者"); 
        Consumer comsumer = new Consumer(pro, "消费者"); 
        Thread t1 = new Thread(producer); 
        Thread t2 = new Thread(comsumer); 
        t1.start(); 
        t2.start(); 
	}

	
}


执行结果如下:
[img=http://img.bbs.csdn.net/upload/201406/24/1403599997_317249.png][/img]
第一轮生产了20个,消费了20个后,程序停止执行。
试着锁product对象,程序会报错停止。
各位大神求指点[img=http://forum.csdn.net/PointForum/ui/scripts/csdn/Plugin/003/monkey/2.gif][/img][img=http://forum.csdn.net/PointForum/ui/scripts/csdn/Plugin/003/monkey/2.gif][/img][img=http://forum.csdn.net/PointForum/ui/scripts/csdn/Plugin/003/monkey/2.gif][/img]

    
   发表时间:2014-06-25  
你的线程 wait了以后 那个地方 唤醒了 你的wait
0 请登录后投票
   发表时间:2014-06-25   最后修改:2014-06-30
//生产者 
public class Producer implements Runnable {

public Product pro = null;
public String user = null;

public Producer(Product pro, String user) {
this.pro = pro;
this.user = user;
}

public void run() {
while (true) {
synchronized (pro) {
if (pro.getProductNum() == 20) {
try {
System.out.println("仓库已满...");
// 唤醒消费
pro.notifyAll();
// 等待
pro.wait();

} catch (Exception e) {
e.printStackTrace();
}
} else if (pro.getProductNum() < 20) {

pro.setProductNum(pro.getProductNum() + 1);
System.out.println("生产了产品:  " + pro.getProductNum());
}
}

}

}

}

//消费者 
public class Consumer implements Runnable {

public Product pro = null;
public String user = null;

public Consumer(Product pro, String user) {
this.pro = pro;
this.user = user;
}

public void run() {
while (true) {
synchronized (pro) {
if (pro.getProductNum() == 0) {
pro.notifyAll();
try {
System.out.println("仓库已空...");
pro.wait();
} catch (Exception e) {
e.printStackTrace();
}
} else if (pro.getProductNum() <= 20) {

System.out.println("消费了产品:  " + pro.getProductNum());
pro.setProductNum(pro.getProductNum() - 1);
}
}

}
}

}
帮你改了,请参考
0 请登录后投票
   发表时间:2014-06-29  
qiaoshaohua 写道
如果锁的是产品对象 那你wait后  产品锁对象是没有释放的  所以会报错,wait后需要notify的
//生产者 
public class Producer implements Runnable {

public Product pro = null;
public String user = null;

public Producer(Product pro, String user) {
this.pro = pro;
this.user = user;
}

public void run() {
while (true) {
synchronized (pro) {
if (pro.getProductNum() == 20) {
try {
System.out.println("仓库已满...");
// 唤醒消费
pro.notifyAll();
// 等待
pro.wait();

} catch (Exception e) {
e.printStackTrace();
}
} else if (pro.getProductNum() < 20) {

pro.setProductNum(pro.getProductNum() + 1);
System.out.println("生产了产品:  " + pro.getProductNum());
}
}

}

}

}

//消费者 
public class Consumer implements Runnable {

public Product pro = null;
public String user = null;

public Consumer(Product pro, String user) {
this.pro = pro;
this.user = user;
}

public void run() {
while (true) {
synchronized (pro) {
if (pro.getProductNum() == 0) {
pro.notifyAll();
try {
System.out.println("仓库已空...");
pro.wait();
} catch (Exception e) {
e.printStackTrace();
}
} else if (pro.getProductNum() <= 20) {

System.out.println("消费了产品:  " + pro.getProductNum());
pro.setProductNum(pro.getProductNum() - 1);
}
}

}
}

}
帮你改了,请参考

纠正一下,wait的时候是有释放锁的,notify是唤醒某一个正在等待该锁的线程去获取对应的锁。
0 请登录后投票
   发表时间:2014-06-30  
234390216 写道
qiaoshaohua 写道
如果锁的是产品对象 那你wait后  产品锁对象是没有释放的  所以会报错,wait后需要notify的
//生产者 
public class Producer implements Runnable {

public Product pro = null;
public String user = null;

public Producer(Product pro, String user) {
this.pro = pro;
this.user = user;
}

public void run() {
while (true) {
synchronized (pro) {
if (pro.getProductNum() == 20) {
try {
System.out.println("仓库已满...");
// 唤醒消费
pro.notifyAll();
// 等待
pro.wait();

} catch (Exception e) {
e.printStackTrace();
}
} else if (pro.getProductNum() < 20) {

pro.setProductNum(pro.getProductNum() + 1);
System.out.println("生产了产品:  " + pro.getProductNum());
}
}

}

}

}

//消费者 
public class Consumer implements Runnable {

public Product pro = null;
public String user = null;

public Consumer(Product pro, String user) {
this.pro = pro;
this.user = user;
}

public void run() {
while (true) {
synchronized (pro) {
if (pro.getProductNum() == 0) {
pro.notifyAll();
try {
System.out.println("仓库已空...");
pro.wait();
} catch (Exception e) {
e.printStackTrace();
}
} else if (pro.getProductNum() <= 20) {

System.out.println("消费了产品:  " + pro.getProductNum());
pro.setProductNum(pro.getProductNum() - 1);
}
}

}
}

}
帮你改了,请参考

纠正一下,wait的时候是有释放锁的,notify是唤醒某一个正在等待该锁的线程去获取对应的锁。

对,是这样的,当时忘了删除了,抱歉啊。。。。
0 请登录后投票
论坛首页 Java企业应用版

跳转论坛:
Global site tag (gtag.js) - Google Analytics