三个线程ABC,交替打印ABC
转载与:https://www.cnblogs.com/x_wukong/p/4009709.html
创建3个线程,让其交替打印ABC 。 输出如下:ABCABCABCABC。
方法:使用synchronized关键字和wait()、notify()
主要的思想就是,为了控制执行的顺序,必须要先持有a锁,也就是前一个线程要释放自身对象锁,再去申请自身对象锁,两者兼备时打印字母,之后首先调用b.notify()释放自身对象锁,唤醒下一个等待线程,再调用a.wait()释放a对象锁,终止当前线程,等待循环结束后再次被唤醒。程序运行的主要过程就是A线程最先运行,持有C,A对象锁,后释放A,C锁,唤醒B。线程B等待A锁,再申请B锁,后打印B,再释放B,A锁,唤醒C,线程C等待B锁,再申请C锁,后打印C,再释放C,B锁,唤醒A……
为了防止线程A,B,C顺序启动,因此在启动a线程之后要让线程休眠,然后启动线程B,再启动线程C。
要注意的是notify()可以将下一个想要获得该锁的线程唤醒。wait()可以释放锁。
package threadforme; public class ThreadWait extends Thread{ private String name; private Object a; private Object b; public ThreadWait(String name,Object a,Object b) { this.name=name; this.a=a; this.b=b; } public void run() { int count=10; while(count>0) { synchronized(a) {//先获得a锁,进入临界区 synchronized(b) { count--; System.out.print(name); b.notify(); //在完成打印之后,将b的阻塞线程唤醒 } try { a.wait(); //调用wait方法终止当前线程 } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } }} } }
package threadforme; public class ThreadTest {public static void main(String[] args) throws InterruptedException { Object a=new Object(); Object b=new Object(); Object c=new Object(); ThreadWait t1=new ThreadWait("A",c,a); //先获得C锁,然后对打印A的过程进行锁定,再释放A锁,再释放C锁 ThreadWait t2=new ThreadWait("B",a,b); //按照顺序获得A锁,获得B锁,打印B ThreadWait t3=new ThreadWait("C",b,c); t1.start(); Thread.sleep(20); t2.start(); Thread.sleep(20); t3.start(); }}
【三个线程ABC,交替打印ABC】
package threadforme;
public class ThreadTest {public static void main(String[] args) throws InterruptedException {Object a=new Object(); Object b=new Object(); Object c=new Object(); ThreadWait t1=new ThreadWait("A",c,a); //先获得C锁,然后对打印A的过程进行锁定,再释放A锁,再释放C锁ThreadWait t2=new ThreadWait("B",a,b); //按照顺序获得A锁,获得B锁,打印BThreadWait t3=new ThreadWait("C",b,c); t1.start(); t2.start(); t3.start(); }
}
转载于:https://www.cnblogs.com/patatoforsyj/p/9579884.html
推荐阅读
- 放屁有这三个特征的,请注意啦!这说明你的身体毒素太多
- CET4听力微技能一
- Linux下面如何查看tomcat已经使用多少线程
- 多线程NSOperation
- 普通人进阶的三个过程-很多人都知道,但却本末倒置
- 2019-11-24|2019-11-24 第三个复盘日
- 内容平台做电商的三个优势
- spring|spring boot中设置异步请求默认使用的线程池
- Android中非UI主线程能不能操作UI()
- CountDownLatch-线程并发的发令枪