1.方法awaitUninterruptibly()的使用
创建名称为4.1.14的项目,类Service.java代码如下:
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;
public class Service {
private ReentrantLock lock = new ReentrantLock();
private Condition condition = lock.newCondition();
public void testMethod() {
try {
lock.lock();
System.out.println("wait begin");
condition.await();
System.out.println("wait end");
} catch (InterruptedException e) {
e.printStackTrace();
System.out.println("catch");
} finally {
lock.unlock();
}
}
}
线程类MyThread.java代码如下:
public class MyThread extends Thread {
private Service service;
public MyThread(Service service) {
super();
this.service = service;
}
@Override
public void run() {
service.testMethod();
}
}
运行类Run.java代码如下:
public class Run {
public static void main(String[] args) {
try {
Service service = new Service();
MyThread myThread = new MyThread(service);
myThread.start();
Thread.sleep(3000);
myThread.interrupt();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
程序运行后出现异常,这是正常现象。结果如下所示:
wait begin
java.lang.InterruptedException
at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.reportInterruptAfterWait(AbstractQueuedSynchronizer.java:2017)
at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.await(AbstractQueuedSynchronizer.java:2052)
at Service.testMethod(Service.java:10)
at MyThread.run(MyThread.java:9)
catch
更改Service.java代码如下:
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;
public class Service {
private ReentrantLock lock = new ReentrantLock();
private Condition condition = lock.newCondition();
public void testMethod() {
try {
lock.lock();
System.out.println("wait begin");
condition.awaitUninterruptibly();
System.out.println("wait end");
} finally {
lock.unlock();
}
}
}
程序运行后的结果如下:
wait begin
正常运行并没有报错
2.方法awaitUntil()的用法
创建项目4.1.15,两个线程类代码如下:
MyThreadA.java
public class MyThreadA extends Thread {
private Service service;
public MyThreadA(Service service) {
super();
this.service = service;
}
@Override
public void run() {
service.waitMethod();
}
}
MyThreadB.java
public class MyThreadB extends Thread {
private Service service;
public MyThreadB(Service service) {
super();
this.service = service;
}
@Override
public void run() {
service.waitMethod();
}
}
类Service.java代码如下:
import java.util.Calendar;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;
public class Service {
private ReentrantLock lock = new ReentrantLock();
private Condition condition = lock.newCondition();
public void waitMethod() {
try {
Calendar calendarRef = Calendar.getInstance();
calendarRef.add(Calendar.SECOND, 10);
lock.lock();
System.out.println("wait begin timer="+System.currentTimeMillis());
condition.awaitUntil(calendarRef.getTime());
System.out.println("wait end timer="+System.currentTimeMillis());
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}
public void notifyMethod() {
try {
Calendar calendarRef = Calendar.getInstance();
calendarRef.add(Calendar.SECOND, 10);
lock.lock();
System.out.println("notify begin timer="+System.currentTimeMillis());
condition.signalAll();
System.out.println("notify end timer="+System.currentTimeMillis());
} finally {
lock.unlock();
}
}
}
创建运行类Run1.java代码如下:
public class Run1 {
public static void main(String[] args) throws InterruptedException {
Service service = new Service();
MyThreadA myThreadA = new MyThreadA(service);
myThreadA.start();
}
}
程序运行结果如下所示:
wait begin timer=1661399159557
wait end timer=1661399169561
10秒后自动唤醒自己
创建运行类Run2.java代码如下:
public class Run2 {
public static void main(String[] args) throws InterruptedException {
Service service = new Service();
MyThreadA myThreadA = new MyThreadA(service);
myThreadA.start();
Thread.sleep(2000);
MyThreadB myThreadB = new MyThreadB(service);
myThreadB.start();
}
}
运行结果如下所示:
wait begin timer=1661414500822
wait begin timer=1661414502808
wait end timer=1661414510828
wait end timer=1661414512815
2秒后被其他线程所唤醒
说明线程在等待时间到达前,可以被其他线程提前唤醒。
3.使用Condition实现顺序执行
使用Condition对象可以对线程执行的业务进行排序规划。
创建项目4.1.16,类F.java代码如下:
public class F {
volatile public static int nextPrintWho = 1;
}
创建运行类Run.java代码如下:
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;
public class Run {
volatile private static int nextPrintWho = 1;
private static ReentrantLock lock = new ReentrantLock();
final private static Condition conditionA = lock.newCondition();
final private static Condition conditionB = lock.newCondition();
final private static Condition conditionC = lock.newCondition();
public static void main(String[] args) {
Thread threadA = new Thread() {
public void run() {
try {
lock.lock();
while (nextPrintWho != 1) {
conditionA.await();
}
for (int i = 0; i < 3; i++) {
System.out.println("ThreadA" + (i + 1));
}
nextPrintWho = 2;
conditionB.signalAll();
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}
};
Thread threadB = new Thread() {
public void run() {
try {
lock.lock();
while (nextPrintWho != 2) {
conditionB.await();
}
for (int i = 0; i < 3; i++) {
System.out.println("ThreadB" + (i + 1));
}
nextPrintWho = 3;
conditionC.signalAll();
} catch (InterruptedException e) {
e.printStackTrace();
}
finally {
lock.unlock();
}
}
};
Thread threadC = new Thread() {
public void run() {
try {
lock.lock();
while (nextPrintWho != 3) {
conditionC.await();
}
for (int i = 0; i < 3; i++) {
System.out.println("ThreadC" + (i + 1));
}
nextPrintWho = 1;
conditionA.signalAll();
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}
};
Thread[] aArray = new Thread[5];
Thread[] bArray = new Thread[5];
Thread[] cArray = new Thread[5];
for (int i = 0; i < 5; i++) {
aArray[i] = new Thread(threadA);
bArray[i] = new Thread(threadB);
cArray[i] = new Thread(threadC);
aArray[i].start();
bArray[i].start();
cArray[i].start();
}
}
}
程序运行结果如下所示:
ThreadA1
ThreadA2
ThreadA3
ThreadB1
ThreadB2
ThreadB3
ThreadC1
ThreadC2
ThreadC3
ThreadA1
ThreadA2
ThreadA3
ThreadB1
ThreadB2
ThreadB3
ThreadC1
ThreadC2
ThreadC3
ThreadA1
ThreadA2
ThreadA3
ThreadB1
ThreadB2
ThreadB3
ThreadC1
ThreadC2
ThreadC3
ThreadA1
ThreadA2
ThreadA3
ThreadB1
ThreadB2
ThreadB3
ThreadC1
ThreadC2
ThreadC3
ThreadA1
ThreadA2
ThreadA3
ThreadB1
ThreadB2
ThreadB3
ThreadC1
ThreadC2
ThreadC3
按顺序打印
以上代码下载请点击该链接:https://github.com/Yarrow052/Java-package.git