一:线程间的相互作用
多线程之间的通信,可以通过wait和notify方法实现,因为wait和notify都是object类中的方法,因此所有的类都有wait和notify方法。
需要注意的是wait,notify方法都必须在同步方法或者同步代码块中执行,因为在调用wait和nofity方法前,必须获得该对象的对象级别锁,当调用wait()方法后,当前线程释放锁,但是调用notify()方法,锁并不会马上释放。
1.1 wait()方法
wait()方法使得当前线程必须要等待,等到另外一个线程调用notify()或者notifyAll()方法,但是带参数的wait(long)方法在等待了一定时间后,如果还没有收到唤醒的通知,那么其会自动唤醒。
1.2 notify()方法
notify()方法会唤醒一个等待当前对象的锁的线程,notifyAll()方法可以使所有在等待队列中等待的线程进入可运行状态,需要注意的是,并不一定是优先级最高的线程最先执行。
二:程序实例
多生产着,多消费者的等待通知,list的大小永远不会大于1
public class MyWaitNotifyAll {
private List<String> list = new ArrayList<String>();
synchronized public void push() {
while (list.size() == 1) {
try {
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
list.add("product one");
this.notifyAll();
System.out.println("生产了:" + list.size() + "个面包");
}
synchronized public void pop() {
while (list.size() == 0) {
try {
System.out.println("没有面包可消费 了:" + Thread.currentThread().getName() + "线程呈wait状 态");
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
list.remove(0);
this.notifyAll();
//notify不是立即释放锁,得等该方法执行完后才释放锁
System.out.println("消费完还剩:" + list.size() + "个面包");
}
}
public class ThreadA extends Thread {
private MyWaitNotifyAll myWaitNotifyAll;
public ThreadA(MyWaitNotifyAll myWaitNotifyAll) {
this.myWaitNotifyAll = myWaitNotifyAll;
}
@Override
public void run() {
while(true){
myWaitNotifyAll.push();
}
}
}
public class ThreadB extends Thread {
private MyWaitNotifyAll myWaitNotifyAll;
Public ThreadB(MyWaitNotifyAll myWaitNotifyAll) {
this.myWaitNotifyAll = myWaitNotifyAll;
}
@Override
public void run() {
while(true){
myWaitNotifyAll.pop();
}
}
}
public class TestMyObject {
public static void main(String[] args) {
MyWaitNotifyAll myStack = new MyWaitNotifyAll();
ThreadA threadA = new ThreadA(myStack);
ThreadA threadA2 = new ThreadA(myStack);
ThreadA threadA3 = new ThreadA(myStack);
ThreadB threadB = new ThreadB(myStack);
ThreadB threadB2 = new ThreadB(myStack);
ThreadB threadB3 = new ThreadB(myStack);
threadA.start();
threadA2.start();
threadA3.start();
threadB.start();
threadB2.start();
threadB3.start();
}
}
运行结果如下:
没有面包可消费了:Thread-3线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-4线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-3线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-5线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-3线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-4线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-3线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-5线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-3线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-4线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-3线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-5线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-3线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-4线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-3线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-5线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-3线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-4线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-3线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
没有面包可消费了:Thread-5线程呈wait状态
生产了:1个面包
消费完还剩:0个面包
..................................