问题:如何实现三线程交替打印?例子:线程1打印A,线程2打印B,线程3打印C,需要交替打印,可以循环打印。输出结果类似:ABCABCABC难度为五颗星,面试中经常遇到。如果是第一次看到这道题,短时间内很难想出合理的解法。如果只需要交替打印一次,实现比较简单,可以使用Thread.join()方法,一个线程等待另一个线程完成。现在要求循环打印涉及到线程间通信,必须要用到锁,一把锁肯定是不行的。例如,线程1释放锁后,线程2和线程3都可能随机获得锁。现在要求线程2必须获取锁,所以需要三把锁。执行过程:线程1获取A锁,打印A,释放B锁;线程2获取B锁,打印B,释放C锁;线程3获取C锁,打印C,释放A锁;循环执行;可以使用Synchronized或者ReentrantLock实现,但是它们无法控制线程启动后的执行顺序。因为三个线程启动后都是等待CPU调度执行,而CPU调度的顺序是随机的,所以并不能保证线程1先执行。有一种简单的实现方法可以控制线程启动后的执行顺序,那就是使用Semaphore(信号量),它可以控制对共享资源的访问次数。使用方法:初始化时指定共享资源个数//初始化一个资源Semaphoresemaphore=newSemaphore(1);获取资源,获取资源后,信号量资源个数减1变为0,其他线程获取资源semaphore.acquire();释放资源,信号量资源数加1,其他阻塞的线程可以获取资源。信号量.release();代码实现:/***@authoryideng*@apiNote三线程循环打印*/publicclassCirclePrint{staticclassThreadDemoextendsThread{privateSemaphorecurrent;接下来是私有信号量;私有字符串名称;/***构造方法*@paramcurrent当前要获取的锁*@paramnext下一个要释放的锁*@paramname打印内容*/publicThreadDemo(Semaphorecurrent,Semaphorenext,Stringname){this.current=当前的;这个.下一个=下一个;this.name=名称;}@Overridepublicvoidrun(){for(inti=0;i<5;i++){try{//获取当前锁,然后打印current.acquire();System.out.print(名字);}catch(InterruptedExceptione){e.printStackTrace();}//释放下一个锁next.release();}}}publicstaticvoidmain(String[]args){//初始化三把锁,只有A把锁可用SemaphoreA=newSemaphore(1);信号量B=新信号量(0);信号量C=新信号量(0);//创建并启动三个线程,线程1获取A锁,释放B锁newThreadDemo(A,B,"A").start();//线程2获取B锁并释放C锁newThreadDemo(B,C,"B").start();//线程3获取C锁,释放A锁newThreadDemo(C,A,"C").start();}}输出结果:ABCABCABCABC你怎么看?有更简单的解决方案吗?
