1、wait()、notify()、notifyAll()方法简介

方法名描述
notify()在 object 上正在 waitSet 等待的线程中挑一个唤醒
notifyAll()让 object 上正在 waitSet 等待的线程全部唤醒,随机一个线程获得锁
wait()让进入 object 监视器的线程到 waitSet 等待
wait(long n)有时限的等待, 到 n 毫秒后结束等待,或是被 notify

2、wait()和sleep()的区别?

  • wait是object的方法,sleep是thread的方法
  • sleep不用强制的synchronize配合使用,wait需要和synchronize配合使用
  • sleep不会释放锁,wait释放锁
  • 他们的状态都为time_waiting

3、模式之保护性暂停

package com.unfbx.test.design;

import lombok.extern.slf4j.Slf4j;

/**
 * @Description
 * 保护性暂停模式
 * @Author Grt
 * @Date 2021-08-09
 */
@Slf4j(topic = "c.GuardedObjectTest")
public class GuardedObjectTest {

    public static void main(String[] args) {
        //需要返回的对象
        GuardedObject guardedObject = new GuardedObject();

        new Thread(() -> {
            //等待结果
            log.info("等待结果!");
            Object response = guardedObject.getResponse();
            log.info("结果是:{}",response.toString());
        },"T1").start();

        new Thread(() -> {
            log.info("执行操作,获取结果...........");
            try {
                Thread.sleep(10000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            guardedObject.complete("我爱你中国!!!!");
        },"T2").start();
    }

}
class GuardedObject{
    //持有的结果
    private Object response;
    /**
    * 不带超时时间的获取结果
    **/
    public Object getResponse(){
        synchronized (this){
            //没有响应结果,继续等待
            while (response == null){
                try {
                    this.wait();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
            return response;
        }
    }

    /**
    * 完成后  设置结果,唤醒等待线程
    **/
    public void complete(Object response){
        synchronized (this){
            this.response = response;
            this.notifyAll();
        }
    }
}

经过改进增加超时机制的保护性暂停模式,只有一个方法存在改动。

    /**
     * 增加超时时间
     * @param timeout
     * @return
     */
    public Object getResponse(long timeout){
        synchronized (this){
            //开始时间
            long begin = System.currentTimeMillis();
            long passedTime = 0;//已经等待的时间
            while (response == null){
                long waitTime = timeout - passedTime;
                if(waitTime <= 0){
                    break;
                }
                try {
                    this.wait(waitTime);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                passedTime = System.currentTimeMillis() - begin;
            }
            return response;
        }
    }
文章目录