java三线程循环有序打印ABC

迅雷笔试题:

编写一个程序,开启 3个线程,这 3个线程的 ID分别为 A、 B、 C,每个线程将自己的 ID在屏幕上打印 10遍,要求输出结果必须按 ABC的顺序显示;如: ABCABC….依次递推。

解决思路:每个线程运行时先检查他依赖的线程是否已完成工作,线程B依赖线程A的完成,线程C依赖线程B和线程A的完成,线程A依赖线程C的完成。如果当前线程依赖的线程没有执行完,则阻塞当前线程直到条件满足再执行。

Condition.await()会使当前线程暂时阻塞,并释放ReentrantLock锁.

Condition .signalAll()会通知激活 Condition.await()而阻塞的线程,这时被激活的线程就会继续检查(通过while循环))是否满足条件,如果满足而且再次获得ReentrantLock锁就能继续运行,否则继续等待。

 1 import java.util.concurrent.locks.Condition;
 2 import java.util.concurrent.locks.ReentrantLock;
 3 
 4 public class ThreadDemo implements Runnable {
 5 
 6     private ReentrantLock lock = new ReentrantLock();
 7     private Condition condition = lock.newCondition();
 8     //标记线程A的状态,true为刚执行完。为什么要两个变量?因为只使用一个变量,当线程A执行完后,a为true,B线程就会不停执行
 9     //所以线程B执行要执行必须满足a==true&&a2==true
10     private volatile Boolean a = false, a2 = false;
11     //标记线程B的状态,true为刚执行完。
12     private volatile Boolean b = false;
13     //标记线程C的状态,true为刚执行完。
14     private volatile Boolean c = true;
15 
16     @Override
17     public void run() {
18         String name = Thread.currentThread().getName();
19         lock.lock();
20         //进入临界区
21         try {
22             for (int i = 0; i < 10; i++) {
23                 if (name.equals("B")) {
24                     //只有a和a2同时为true时才打印B,否则阻塞当前线程
25                     while (!a || !a2) {
26                         condition.await();//条件不满足,暂时阻塞线程,暂时释放lock
27                     }
28                     b = true;
29                     a2 = false;
30                 } else if (name.equals("C")) {
31                     while (!a || !b) {
32                         condition.await();
33                     }
34                     c = true;
35                     b = false;
36                 } else if (name.equals("A")) {
37                     while (!c) {
38                         condition.await();
39                     }
40                     a = true;
41                     a2 = true;
42                     b = false;
43                     c = false;
44                 }
45                 System.out.print(name);
46                 condition.signalAll();//通知正在等待的线程,此时有可能已经满足条件
47             }
48         } catch (InterruptedException e) {
49             e.printStackTrace();
50         } finally {
51             lock.unlock();// 记得要释放锁
52         }
53     }
54 
55     public static void main(String[] args) throws InterruptedException {
56         ThreadDemo task = new ThreadDemo();
57         Thread thread1 = new Thread(task);
58         Thread thread2 = new Thread(task);
59         Thread thread3 = new Thread(task);
60         thread1.setName("A");
61         thread2.setName("B");
62         thread3.setName("C");
63         thread1.start();
64         thread2.start();
65         thread3.start();
66     }
67 
68 }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值