目录

java多线程中-用于同步控制的各种方法作用

java多线程中-用于同步控制的各种方法作用


1 wait() / notify() / notifyAll()

作用

wait() 让当前线程进入等待队列 ,同时释放锁 ,直到 notify()notifyAll() 唤醒。

方法定义

void wait() // 让当前线程进入等待状态 void wait(long timeout) // 等待指定时间后超时返回 void wait(long timeout, int nanos) // 更精细的超时控制 void notify() // 唤醒在该对象监视器上等待的一个线程 void notifyAll() // 唤醒所有等待的线程

特点

  1. 必须在synchronized 代码块或方法中调用,否则会抛出 IllegalMonitorStateException
  2. wait() 调用后释放锁 ,等待 notify()notifyAll() 唤醒。
  3. notify() 只唤醒一个 等待的线程,notifyAll() 唤醒所有等待线程
  4. 唤醒后线程需要重新竞争锁 ,才能继续执行。

示例

class WaitNotifyExample { private static final Object lock = new Object(); public static void main(String[] args) { Thread threadA = new Thread(() -> { synchronized (lock) { try { System.out.println(“线程 A:等待…”); lock.wait(); System.out.println(“线程 A:被唤醒,继续执行”); } catch (InterruptedException e) { e.printStackTrace(); } } }); Thread threadB = new Thread(() -> { synchronized (lock) { System.out.println(“线程 B:唤醒线程 A”); lock.notify(); } }); threadA.start(); try { Thread.sleep(1000); } catch (InterruptedException e) {} threadB.start(); } }


2 park() / unpark()

作用

park() 让线程进入阻塞状态unpark() 唤醒线程。

方法定义

void LockSupport.park() // 挂起当前线程 void LockSupport.parkNanos(long nanos) // 挂起指定纳秒 void LockSupport.parkUntil(long deadline) // 挂起直到某个时间点 void LockSupport.unpark(Thread thread) // 唤醒指定的线程

特点

  1. 不依赖synchronized,可以直接调用。
  2. 不会释放锁 ,与 wait() 的行为不同。
  3. unpark(thread) 可以先调用,再调用 park() 也不会影响结果。
  4. park() 使用许可机制 ,每次 unpark() 只给一个线程一个许可

示例

import java.util.concurrent.locks.LockSupport; class ParkUnparkExample { public static void main(String[] args) { Thread thread = new Thread(() -> { System.out.println(“线程 A:等待被唤醒…”); LockSupport.park(); System.out.println(“线程 A:被唤醒,继续执行”); }); thread.start(); try { Thread.sleep(1000); } catch (InterruptedException e) {} System.out.println(“主线程:唤醒线程 A”); LockSupport.unpark(thread); } }


3 interrupt()

作用

interrupt() 让线程从阻塞等待 状态中被打断,并抛出 InterruptedException

方法定义

void Thread.interrupt() // 中断线程 boolean Thread.isInterrupted() // 检测是否被中断 static boolean Thread.interrupted() // 检测当前线程是否被中断,并清除中断标志

特点

  1. interrupt() 只是标记线程被中断 ,不会真正终止线程。
  2. 如果线程正在sleep()wait()park(),会抛 InterruptedException 并清除中断状态
  3. isInterrupted() 仅检查中断状态,不清除interrupted() 既检查又清除

示例

class InterruptExample { public static void main(String[] args) { Thread thread = new Thread(() -> { while (!Thread.currentThread().isInterrupted()) { System.out.println(“线程 A 正在运行…”); try { Thread.sleep(1000); } catch (InterruptedException e) { System.out.println(“线程 A 被中断,退出循环”); break; } } }); thread.start(); try { Thread.sleep(3000); } catch (InterruptedException e) {} thread.interrupt(); } }


4 sleep()

作用

让线程休眠一段时间,不释放锁。

方法定义

void Thread.sleep(long millis) void Thread.sleep(long millis, int nanos)

特点

  1. sleep() 不会释放锁 ,只是让线程暂停执行。
  2. sleep() 期间如果被 interrupt() 调用,会抛 InterruptedException 并立即返回。

示例

class SleepExample { public static void main(String[] args) { Thread thread = new Thread(() -> { try { System.out.println(“线程 A:休眠 2 秒…”); Thread.sleep(2000); System.out.println(“线程 A:休眠结束,继续执行”); } catch (InterruptedException e) { System.out.println(“线程 A 被中断”); } }); thread.start(); } }


5 yield()

作用

让当前线程主动让出 CPU 资源,进入就绪状态

方法定义

static void Thread.yield()

特点

  1. yield() 不会释放锁 ,只是让出 CPU,仍然可能马上重新调度到该线程。
  2. yield() 只是一个提示 ,不保证会立即让出 CPU。

示例

class YieldExample { public static void main(String[] args) { Thread thread = new Thread(() -> { for (int i = 0; i < 5; i++) { System.out.println(“线程 A 运行:” + i); Thread.yield(); } }); thread.start(); } }


6 join()

作用

让当前线程等待另一个线程执行完毕

方法定义

void Thread.join() void Thread.join(long millis)

特点

  1. join()调用线程等待目标线程执行完毕
  2. 可以指定超时,避免无限等待。

示例

class JoinExample { public static void main(String[] args) { Thread thread = new Thread(() -> { System.out.println(“线程 A:执行任务…”); try { Thread.sleep(2000); } catch (InterruptedException e) {} System.out.println(“线程 A:任务完成”); }); thread.start(); try { thread.join(); } catch (InterruptedException e) {} System.out.println(“主线程:等待线程 A 结束后继续执行”); } }


7 线程同步方法对比

方法释放锁作用唤醒方式
wait()进入等待队列notify() / notifyAll()
park()阻塞线程unpark(thread)
sleep()休眠线程时间结束或 interrupt()
interrupt()中断线程抛出 InterruptedException
join()等待另一个线程结束目标线程执行完毕