首页 > 代码库 > Java Day 14
Java Day 14
多线程--线程间通信
对同一个资源进行处理,但是任务却不同
线程间通信--等待唤醒机制
1、wait(); 线程处于冻结状态,被wait线程存储在线程池中
2、notify(); 从线程池唤醒一个线程
3、notifyAll(); 唤醒所有线程
方法必须定义在同步中
为什么操作线程的方法wait notify notifyAll定义在Object类中
因为这些方法是监视器的方法,监视器其实就是锁
锁可以是任意的对象,任意的对象调用的方式一定是定义在Object类中
唤醒--代码优化
多生产者多消费者
多生产多消费者问题解决
notifyAll();
while判断标记,解决了线程获取执行权后是否重新运行
notifyAll()解决了本方线程一定唤醒对方线程
多生产多消费问题 JDK1.5新特性 -- Lock
同步代码块,对于锁的操作是隐式的。
1 import java.util.concurrent.locks.*; 2 //import java.util.condition; 3 class Resource{ 4 private String name; 5 private int count = 1; 6 private boolean flag = false; 7 Lock lock = new ReentrantLock(); 8 //Condition c1 = lock.newCondition(); 9 Condition pro_con = lock.newCondition();10 Condition cos_con = lock.newCondition();11 12 Resource(){}13 14 public void set(String name){//synchronized15 lock.lock();16 try{17 while(flag)//while(flag)--死锁18 //try{wait();}catch(InterruptedException e){}19 try{pro_con.await();}catch(InterruptedException e){}20 this.name = name + count;21 count++;22 System.out.println(Thread.currentThread().getName()+": 生产..5.0. "+this.name);23 flag = true;24 //notifyAll();//notifyAll()25 //c1.signalAll();//notifyAll()26 cos_con.signal();//notifyAll()27 }28 finally{29 lock.unlock();30 }31 32 33 }34 35 public void out(){ //synchronized36 lock.lock();37 try{38 while(!flag)//while(flag)--出现死锁--notifyAll()39 try{cos_con.await();}catch(InterruptedException e){}40 System.out.println(Thread.currentThread().getName()+":...消费了......"+name);41 flag = false;42 //notifyAll();//notifyAll()}43 //c1.signalAll();44 pro_con.signal();45 46 }47 finally{48 lock.unlock();//notifyAll()49 } 50 }51 }52 53 class Producer implements Runnable{54 private Resource r;55 Producer(Resource r){56 this.r = r;57 }58 59 public void run(){60 while(true){61 r.set("烤鸭");62 }63 64 }65 }66 67 class Consumer implements Runnable{68 private Resource r;69 Consumer(Resource r){70 this.r = r;71 }72 public void run(){73 while(true){74 r.out();75 } 76 }77 }78 79 class ProduceConsumerDemo{80 public static void main(String[] args){81 Resource r = new Resource();82 Producer pro = new Producer(r);83 Consumer con = new Consumer(r);84 85 Thread t0 = new Thread(pro);86 Thread t1 = new Thread(pro);87 Thread t2 = new Thread(con);88 Thread t3 = new Thread(con);89 90 t0.start();91 t1.start();92 t2.start();93 t3.start();94 95 }96 }
将同步和锁封装成了对象
JDK1.5新特性--condition
wait notify notifyAll
JDK1.5解决方法
一个锁多个监视器
范例
Lock 接口:替代了同步代码块或同步函数,由隐式锁操作变成显示
lock() 获取锁
unlock() 释放锁 在finally代码块中
Condition 接口 替代了Object中的wait notify notifyAll方法,单独进行封装
await
signal
signalAll
1 class BoundedBuffer { 2 final Lock lock = new ReentrantLock(); 3 final Condition notFull = lock.newCondition(); 4 final Condition notEmpty = lock.newCondition(); 5 6 final Object[] items = new Object[100]; 7 int putptr, takeptr, count; 8 9 public void put(Object x) throws InterruptedException {10 lock.lock();11 try {12 while (count == items.length)13 notFull.await();14 items[putptr] = x;15 if (++putptr == items.length) putptr = 0;16 ++count;17 notEmpty.signal();18 } finally {19 lock.unlock();20 }21 }22 23 public Object take() throws InterruptedException {24 lock.lock();25 try {26 while (count == 0)27 notEmpty.await();28 Object x = items[takeptr];29 if (++takeptr == items.length) takeptr = 0;30 --count;31 notFull.signal();32 return x;33 } finally {34 lock.unlock();35 }36 }37 }
wait sleep 区别
1、wait可以指定时间也可以不指定,sleep必须指定
2、在同步中,对cpu的执行权和锁的处理不同
wait 释放执行权和锁
sleep 释放执行权 不是释放锁
停止线程方式--定义标记
1、stop方法
2、run方法结束
怎么控制线程的任务结束呢?
控制循环就可以结束任务
停止线程方式--Interrupt
如果线程处于冻结状态,无法读取标记,如何结束?
interrupt 将线程从冻结强制恢复成运行状态,但会发生中断异常
守护进程--setDaemon
后台线程,先于线程启动前调用
join方法
setPriority(Thread.MAX_PRIORITY)
yield
Java Day 14