多线程
生产者与消费者(线程通信)
实现生产者和消费者案例(一)
/*
*资源类
*包子
*/
public class Resource {
//定 义布尔类型的成员,标志位,指示线程该做什么
//false没有,需要生产,true需 要消费
boolean flag = false;
int count ;//包子的计数 器
}
/*
*生产者线程,生产资源
*对资源中的变量++
*/
public class Product implements Runnable {
//创建资源对象
Resource r ;
public Product( Resource r) {
this.r = r;
}
public void run() {
whiele(true){
synchronized(r) {//同步技术关键字
//对 象资源进行操作,判断变量
if(r.flag == true) {
//没有被消费,不能生产,等待
try{
r.wait();
}catch( Exception ex){}
}
//可以生产
r . count++;
System . out. println("生产了第"+r. count+"个");
//修改标志位
r. flag=true;//可以消费
//唤醒消费线程
r.notify();
}
}
}
}
/*
*消费者线程,消费资源
*对资源中的变量输出打印
*/
.//创建资源对象
public class Customer implements Runnable{
Resource r ;
public Product( Resource r) {
this.r = r;
}
public void run( ) {
while(true){
synchronized(r) {//同步技术关键字
//判断标志位
if(r.flag == false) {
//需要生产,不能消费,等待
try{
r.wait();
}catch( Exception ex){}
}
//可以消费
System. out . println("消费了第"+r.count+"个") ;
//修改标志位,已经消费,可以生产
r.flag=false;
//唤醒生产线程
r.notify();
}
}
}
}
public static void main(String[] args) {
//创建资源对象
Resource r=new Resource();
//创建生产 者和消费者对象
Product p = new Product(r);
Customer C = new Customer(r);
Thread tθ = new Thread(p);
Thread t1 = new Thread(c);
t0.start();
t1. start();
}
wait() notify(),方法必须出现在同步技术中
解决异常问题,使用同步代码块
生产者线程和消费者线程,使用同一个对象锁, wait() notify()方法调用者必须是锁对象
线程的方法
Object类的方法wait(),Thread类的方法sleep()
- 问题:为什么等待唤醒的方法,定义在了Object类中,而不是Thread
。同步锁导致,任何对象都能作为锁,保证任何一个锁对象,都能调用等待与唤醒 - wait()和sleep()方法区别
。wait()只能出现在同步中,必须是锁对象调用
。sleep()方法可以随时使用,不依赖同步
。wait()方法释放同步锁,被唤醒后,重新获取锁
。sleep()方法不释放同步锁
实现生产者和消费者案例(二)
私有修饰成员变量
/*
*资源类
*包子
*成员变量私有修饰,提供方法对外访问
*/
public class Resource {
//定 义布尔类型的成员,标志位,指示线程该做什么
//false没有,需要生产,true需 要消费
private boolean flag = false;
private int count ;//包子的计数 器
//提供方法,生产
public synchronized void product() {
//判断变量=true,不能生产,等待
if(flag==true )
try{this . wait( );}catch( Exception ex) {ex. printStackTrace();}
count++;
System . out. println("生产了第"+count+"个");
//修改标志位
flag=true;
//唤醒消费线程
this.notify();
}
//提供方法,消费
public synchronized void customer() {
if(flag==false)
try{this . wait( );}catch( Exception ex) {ex. printStackTrace();}
System. out . println("消费了第"+count+"个") ;
//修改标志位
flag=false;
//唤醒生成线程
this.notify();
}
}
/*
*生产者线程,生产资源
*对资源中的变量++
*/
public class Product implements Runnable {
//创建资源对象
private Resource r ;
public Product( Resource r) {
this.r = r;
}
public void run() {
while(true){
r.product();
}
}
}
/*
*消费者线程,消费资源
*对资源中的变量输出打印
*/
.//创建资源对象
public class Customer implements Runnable{
Resource r ;
public Customer ( Resource r) {
this.r = r;
}
public void run( ) {
while(true){
r.customer();
}
}
}
public static void main(String[] args) {
//创建资源对象
Resource r=new Resource();
//创建生产 者和消费者对象
Product p = new Product(r);
Customer C = new Customer(r);
Thread tθ = new Thread(p);
Thread t1 = new Thread(c);
t0.start();
t1. start();
}