java.lang.Object

	// 返回实例运行时的的类型
	public final native Class<?> getClass();
 
    public native int hashCode();
 
    public boolean equals(Object obj) {
        return (this == obj);
    }
 
    protected native Object clone() throws CloneNotSupportedException;
 
     public String toString() {
        return getClass().getName() + "@" + Integer.toHexString(hashCode());
    }
 
    public final native void notify();
 
    public final native void notifyAll();

 
    public final void wait() throws InterruptedException {
        wait(0);
    }
    public final void wait(long timeout, int nanos) throws InterruptedException;
    public final native void wait(long timeout) throws InterruptedException
 
    protected void finalize() throws Throwable { }

  • wait() 导致当前线程进入waiting状态,直至另一个线程调用notify()、notifyAll()方法
  • 当前线程(调用wait()的线程)必须拥有这个对象的(monitor)锁,然后线程释放这个(monitor)锁
         synchronized (obj) {
             while (condition does not hold)
                  obj.wait();
              ... // Perform action appropriate to condition
          }
  • notify() 唤醒一个等待对象锁的线程
  • 只有等当前线程释放了对象锁之后,被唤醒的线程才能够proceed(运行)
  • 被唤醒的线程会和其他线程一样去竞争对象锁资源。
  • 只有拥有对象锁资源的线程才能调用此方法

一个线程获得对象锁(monitor监视器)资源的三种方法(synchronized的三种用法)

  1. By executing a synchronized instance method of that object.
  2. By executing the body of a {@code synchronized} statement that synchronizes on the object.
  3. For objects of type {@code Class,} by executing a synchronized static method of that class.
总结
synchronized(object1) {
	object1.wait();
	System.out.printLn("hello")
}

首先一个线程A尝试获取object1对象的monitor锁,
其实是将object1对象的mark word中引用的MonitorObject对象的_owner设置为当前线程。

如果这时候会有另一个线程B过来,尝试进入同步代码块,尝试获取锁失败,然后会自旋一会,
如还没有成功获取锁,则会将线程B会进入BLOCKED状态,然后线程B被封装成ObjectWaiter
放置object1对象的mark word中引用的MonitorObject对象的_EntryList里。

然后线程A会调用object1.wait();线程A会释放占用的monitor锁,
即 将object1对象的mark word中引用的MonitorObject对象的_owner设置为null。
然后线程A进入WAITING状态,且被被封装成ObjectWaiter放置object1对象的
mark word中引用的MonitorObject对象的_WaitSet里。

synchronized(object1) {
	object1.signal();
}

此时线程C恰好尝试获取object1对象锁,正在自旋,恰好获得了object1对象锁,
这时object1对象的mark word中引用的MonitorObject对象的_owner为线程C。

线程C里调用object1.signal();然后会在object1对象的mark word中引用的
MonitorObject对象的_WaitSet里,随机挑选一个ObjectWaiter并唤醒该线程,
这时线程C还没有释放object1对象锁。

假设恰好唤醒线程A,这时线程A和_EntryList里的线程会竞争锁,

然后当线程A获得监视器锁,将会在直接打印"hello",说明被唤醒后的位置是在await()之后。
被唤醒的线程要从哪里恢复执行呢?当然是被挂起的地方

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

等待/通知的经典范式
synchronized (对象) {
    while (条件不满足) {
        对象.wait();   
    }
    
    对应的逻辑处理
}
 
 
synchronized (对象) {
    改变条件
    对象.notify();
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值