4.2 LockSupport是什么
LockSupport是用来创建锁和其他同步类的基本线程阻塞原语,其中park()和unpack()而作用分别是
阻塞线程和解除阻塞线程.
4.3 线程等待唤醒机制
4.3.1 三种让线程等待和唤醒的方法
-
方式一:使用Object中的wait()方法让线程等待,使用Object中的notify()方法唤醒线程
-
方式二:使用JUC包中的Condition的await()方法让线程等待,使用signal()方法唤醒线程
-
方式三:LockSupport类可以阻塞当前线程以及唤醒指定被阻塞的线程
4.3.2 Object类中的wait和notify方法实现线程等待和唤醒
-
wait和notify方法必须要在同步代码块或者方法里面,且成对出现使用
-
先wait再notify才ok
package com.nanjing.gulimall.zhouyimo.test;
import java.util.concurrent.TimeUnit;
/**
* @author zhou
* @version 1.0
* @date 2023/10/16 9:11 下午
*/
public class LockSupportDemo {
public static void main(String[] args) {
Object objectLock = new Object();
/**
* t1 -----------come in
* t2 -----------发出通知
* t1 -------被唤醒
*/
new Thread(() -> {
synchronized (objectLock) {
System.out.println(Thread.currentThread().getName() + "\t -----------come in");
try {
objectLock.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println(Thread.currentThread().getName() + "\t -------被唤醒");
}
}, "t1").start();
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(() -> {
synchronized (objectLock) {
objectLock.notify();
System.out.println(Thread.currentThread().getName() + "\t -----------发出通知");
}
}, "t2").start();
}
}
t1 -----------come in
t2 -----------发出通知
t1 -------被唤醒
4.3.3 Condition接口中的await和signal方法实现线程的等待和唤醒
-
Condition中的线程等待和唤醒方法,需要先获取锁
-
一定要先await后signal,不要反了
package com.nanjing.gulimall.zhouyimo.test;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
/**
* @author zhou
* @version 1.0
* @date 2023/10/16 9:11 下午
*/
public class LockSupportDemo {
public static void main(String[] args) {
Lock lock = new ReentrantLock();
Condition condition = lock.newCondition();
/**
* t1 -----------come in
* t2 -----------发出通知
* t1 -----------被唤醒
*/
new Thread(() -> {
lock.lock();
try {
System.out.println(Thread.currentThread().getName() + "\t -----------come in");
condition.await();
System.out.println(Thread.currentThread().getName() + "\t -----------被唤醒");
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}, "t1").start();
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(() -> {
lock.lock();
try {
condition.signal();
System.out.println(Thread.currentThread().getName() + "\t -----------发出通知");
} finally {
lock.unlock();
}
}, "t2").start();
}
}
4.3.4 上述两个对象Object和Condition使用的限制条件
-
线程需要先获得并持有锁,必须在锁块(synchronized或lock)中
-
必须要先等待后唤醒,线程才能够被唤醒