wait
- wait 是 Object 类的实例方法,用于线程间通信
- wait() 方法导致当前线程进入等待状态并释放对象的锁,直到它被通知(其他线程调用 notify 或 notifyAll 方法。notify / notifyAll 方法解除等待线程的阻塞状态)
- wait(long timeout) 方法导致当前线程释放对象的锁,并进入等待状态直到它被通知或者经过指定的时间
- wait() 和 wait(long timeout) 被唤醒后会进入阻塞状态(Blocked),直到获得锁,才进入就绪态(Runnable)
- wait() 方法只能在同步方法或同步代码块中调用。如果当前线程不是对象锁的持有者,该方法抛出一个 IllegalMonitorStateException 异常
- 可以通过 interrupt() 方法打断线程的暂停状态,从而使线程立刻抛出 InterruptedException(但不建议使用该方法),被 interrupt 以后会释放锁
- 不需要捕获异常
sleep
- sleep 是 Thread 类的静态方法,作用是阻塞当前线程,让出 CPU 的使用
- 用于短时间暂停当前线程
- sleep(long millis) 使当前线程进入停滞状态,所以执行 sleep() 的线程在指定的时间内肯定不会被执行
- sleep(long millis) 可能使任意优先级的其他线程得到执行机会
- sleep(long millis) 不会释放锁
- 调用 sleep 方法的线程在唤醒之后不保证能获取到 CPU,它会先进入就绪态(Runnable),与其他线程竞争 CPU
- 可以通过 interrupt() 方法打断线程的暂停状态,从而使线程立刻抛出 InterruptedException(但不建议使用该方法),被 interrupt 以后会释放锁
- 需要捕获异常
/**
* Thread sleep和wait区别
*/
public class ThreadTest implements Runnable {
int number = 10;
public void firstMethod() throws Exception {
synchronized (this) {
number += 100;
System.out.println(number);
}
}
public void secondMethod() throws Exception {
synchronized (this) {
/**
* (休息 2s,阻塞线程)
* 以验证当前线程对象的机锁被占用时,
* 是否被可以访问其他同步代码块
*/
Thread.sleep(2000);
// this.wait(2000);
number *= 200;
}
}
@Override
public void run() {
try {
firstMethod();
} catch (Exception e) {
e.printStackTrace();
}
}
public static void main(String[] args) throws Exception {
ThreadTest threadTest = new ThreadTest();
Thread thread = new Thread(threadTest);
thread.start();
threadTest.secondMethod();
}
}
运行结果:
Thread.sleep(2000): 2100
this.wait(2000): 110
yield
- yield 是 Thread 类的静态方法,没有参数,使当前线程从运行状态变为就绪态
- yield 方法使当前线程让出 CPU,但让出的时间是不可设定的
- yield 方法不会释放锁
- yield 会把 CPU 让给相同优先级的其他线程,而不会把 CPU 给更高或更低优先级的其他线程。若此时没有其他线程跟它在有一个优先级,则该线程继续获得 CPU 时间,因此可能某线程刚调用 yield 方法又马上被执行
- 不需要捕获异常