JDK源码笔记--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 native void wait(long timeout) throws InterruptedException;

public final void wait() throws InterruptedException {
        wait(0);
    }

protected void finalize() throws Throwable { }

 重点看看wait(),notify(),notifyAll()方法

首先是都是final native 修饰的。

monitor暂且译成监听器,相当于对象锁。

notify的注释:

    /**
     * Wakes up a single thread that is waiting on this object's
     * monitor. If any threads are waiting on this object, one of them
     * is chosen to be awakened. The choice is arbitrary and occurs at
     * the discretion of the implementation. A thread waits on an object's
     * monitor by calling one of the {@code wait} methods.

 唤醒正在等待该对象的单个线程,如果有多个线程在等待获取某个对象的监听器,只唤醒其中一个。

@throws  IllegalMonitorStateException  if the current thread is not
     *               the owner of this object's monitor.

如果当前线程没拥有监听器就抛异常 IllegalMonitorStateException,这就是为什么notify,notifyAll必须在synchronized代码中执行。

 

notifyAll的注释:

/**
     * Wakes up all threads that are waiting on this object's monitor. A
     * thread waits on an object's monitor by calling one of the
     * {@code wait} methods.

 唤醒在该对象监视器上等待的所有线程,但是只有一个最终获得监听器。

 @throws  IllegalMonitorStateException  if the current thread is not
     *               the owner of this object's monitor.

 同上。

 

wait的注释:

/**
     * Causes the current thread to wait until either another thread invokes the
     * {@link java.lang.Object#notify()} method or the
     * {@link java.lang.Object#notifyAll()} method for this object, or a
     * specified amount of time has elapsed.

 

     * <ul>
     * <li>Some other thread invokes the {@code notify} method for this
     * object and thread <var>T</var> happens to be arbitrarily chosen as
     * the thread to be awakened.
     * <li>Some other thread invokes the {@code notifyAll} method for this
     * object.
     * <li>Some other thread {@linkplain Thread#interrupt() interrupts}
     * thread <var>T</var>.
     * <li>The specified amount of real time has elapsed, more or less.  If
     * {@code timeout} is zero, however, then real time is not taken into
     * consideration and the thread simply waits until notified.
     * </ul>

 

导致当前线程等待,直到另一个线程调用notify(),notifyAll(),线程中断,或者超过指定的时间。

当调用wait(),实际上是调用的wait(0)表示无限等下去,也可以指定如wait(1000)表示等待一秒就继续执行。

wait()方法会放弃对象锁,sleep()不会。

     * the condition that should have caused the thread to be awakened, and
     * continuing to wait if the condition is not satisfied.  In other words,
     * waits should always occur in loops, like this one:
     * <pre>
     *     synchronized (obj) {
     *         while (<condition does not hold>)
     *             obj.wait(timeout);
     *         ... // Perform action appropriate to condition
     *     }
     * </pre>

 建议wait(time)的方法放在while循环中。

     * @throws  IllegalArgumentException      if the value of timeout is
     *               negative.
     * @throws  IllegalMonitorStateException  if the current thread is not
     *               the owner of the object's monitor.
     * @throws  InterruptedException if any thread interrupted the

当时间参数not in the range 0-999999,抛异常IllegalArgumentException

当线程未获得对象锁,抛异常IllegalMonitorStateException。这就是wait()要在synchronized中执行。

当线程被中断,抛异常InterruptedException

 

一个栗子:

public class Test2 implements Runnable {
    static Object a = new Object();
    public static void main(String[] args) throws InterruptedException {
        Test2 t2 = new Test2();
        Thread thread = new Thread(t2);
        thread.start();
        //TimeUnit.MILLISECONDS.sleep(1000);
        synchronized (a) {
            System.out.println("notify start"+System.currentTimeMillis());
            a.notify();
            System.out.println("notify end"+System.currentTimeMillis());
        }
    }

    @Override
    public void run() {
        synchronized (a) {
            try {
                System.out.println("wait start" + System.currentTimeMillis());
                a.wait();
                System.out.println("wait end" + System.currentTimeMillis());
            } catch (InterruptedException e) {
                e.printStackTrace();
            }

        }
    }
}

 当TimeUnit.MILLISECONDS.sleep(1000);注释掉时,控制台:

notify start1517303479751
notify end1517303479752
wait start1517303479752

 notify执行完了才执行wait,导致wait不能结束。意味着执行顺序不能依赖代码先后顺序。

转载于:https://www.cnblogs.com/lanqie/p/8384925.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值