使用wait(1)和Thread.sleep(1)的优缺点

23 浏览
0 Comments

使用wait(1)和Thread.sleep(1)的优缺点

一个线程中的 wait()sleep() 有何不同?

我理解 wait() 的线程仍处于运行模式并使用 CPU 循环,而 sleep() 的线程则不消耗任何 CPU 循环,这是正确的吗?

为什么我们需要同时拥有 wait()sleep()

它们在更低层次的实现方式有何差异?

admin 更改状态以发布 2023年5月21日
0
0 Comments

还未提到的一个主要区别是:

  • sleep() 方法不会释放当前线程的锁,

    synchronized(LOCK) {
        Thread.sleep(1000); // LOCK is held
    }
    

  • wait() 方法释放当前对象的锁。

     synchronized(LOCK) {
         LOCK.wait(); // LOCK is not held
     }
    

0
0 Comments

wait可以被另一个线程调用该锁上面的notify方法唤醒,而sleep则不能。另外,wait(和notify)必须在监视器对象上的同步块中发生,而sleep则不必。

Object mon = ...;
synchronized (mon) {
    mon.wait();
} 

此时,当前执行的线程将等待并释放监视器。另一个线程可能会执行

synchronized (mon) { mon.notify(); }

(在相同的mon对象上),并且第一个线程(假设它是唯一等待监视器的线程)将醒来。

如果有多个线程在等待监视器,你还可以调用notifyAll,这将唤醒它们所有。然而,只有一个线程能够获得监视器(记住wait在同步块中),并且继续执行;其余线程将被阻塞,直到它们能够获得监视器的锁。

另外,你在Object本身(即等待一个对象的监视器)上调用wait,而在Thread上调用sleep

还有一点是,你从wait可能会产生虚假唤醒(即等待的线程无明显原因地恢复。) 你应该始终在某个条件下自旋等待,如下所示:

synchronized {
    while (!condition) { mon.wait(); }
}

0