ABC三个线程交替打印10遍,要求A打印5次,B打印10次,C打印15次

问题:

  ABC三个线程交替打印10遍,要求A打印5次,B打印10次,C打印15

 第一遍
AAAAABBBBBBBBBBCCCCCCCCCCCCCCC
第二遍
AAAAABBBBBBBBBBCCCCCCCCCCCCCCC
...共打印10

1.使用Sychronized+wait()+notify()的方式
package com.yang.test;

/**
 * ABC三个线程交替打印10遍,要求A打印5次,B打印10次,C打印15次
 * 第一遍
 * AAAAABBBBBBBBBBCCCCCCCCCCCCCCC
 * 第二遍
 * AAAAABBBBBBBBBBCCCCCCCCCCCCCCC
 * ...共打印10遍
 * @author yang yajun
 * @date 2020/12/2615:31
 */
public class OrderThreadPrint {

    public static void main(String[] arg0){
        Print print = new Print();

        new Thread(()->{
            for (int i = 0; i < 10; i++) {
                print.printA();
            }
        },"A").start();
        new Thread(()->{
            for (int i = 0; i < 10; i++) {
                print.printB();
            }
        },"B").start();
        new Thread(()->{
            for (int i = 0; i < 10; i++) {
                print.printC();
            }
        },"C").start();
    }
}

class Print{
    private int i = 1;
    public synchronized void  printA(){
        while (i%3!=1) {
            try {
                wait();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        for (int j = 0; j < 5; j++) {
            System.out.print(Thread.currentThread().getName() + i);
        }
        i++;
        notifyAll();
    }
    public synchronized void  printB(){
        while (i%3!=2) {
            try {
                wait();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        for (int j = 0; j < 10; j++) {
            System.out.print(Thread.currentThread().getName()+i);
        }
        i++;
        notifyAll();
    }
    public synchronized void  printC(){
        while (i%3!=0) {
            try {
                wait();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        for (int j = 0; j < 15; j++) {
            System.out.print(Thread.currentThread().getName() + i);
        }
        i++;
        notifyAll();
    }

}
2.使用Lock(Condition)+await()+signal()来实现
package com.yang.test;

import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * ABC三个线程交替打印10遍,要求A打印5次,B打印10次,C打印15次
 * 第一遍
 * AAAAABBBBBBBBBBCCCCCCCCCCCCCCC
 * 第二遍
 * AAAAABBBBBBBBBBCCCCCCCCCCCCCCC
 * ...共打印10遍
 * @author yang yajun
 * @date 2020/12/2615:31
 */
public class OrderThreadPrintLock {

    public static void main(String[] arg0){
        PrintLk print = new PrintLk();

        new Thread(()->{
            for (int i = 0; i < 10; i++) {
                print.printA();
            }
        },"A").start();
        new Thread(()->{
            for (int i = 0; i < 10; i++) {
                print.printB();
            }
        },"B").start();
        new Thread(()->{
            for (int i = 0; i < 10; i++) {
                print.printC();
            }
        },"C").start();
    }
}

class Print{
    private int i = 1;
    private Lock lock = new ReentrantLock();
    private Condition condition1 = lock.newCondition();
    private Condition condition2 = lock.newCondition();
    private Condition condition3 = lock.newCondition();

    public synchronized void  printA(){
        lock.lock();
        try {
            while (i!=1) {//判断,多线程通信,使用while代替if
                try {
                    condition1.await();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        //干活 for (int j = 0; j < 5; j++) { System.out.print(Thread.currentThread().getName() + i); } i=2; condition2.signal();//通知 }finally { lock.unlock(); } } public synchronized void printB(){ lock.lock(); try { while (i!=2) { try { condition2.await(); } catch (InterruptedException e) { e.printStackTrace(); } } for (int j = 0; j < 10; j++) { System.out.print(Thread.currentThread().getName()+i); } i=3; condition3.signal(); }finally { lock.unlock(); } } public synchronized void printC(){ lock.lock(); try { while (i!=3) { try { condition3.await(); } catch (InterruptedException e) { e.printStackTrace(); } } for (int j = 0; j < 15; j++) { System.out.print(Thread.currentThread().getName() + i); } i=1; condition1.signal(); }finally { lock.unlock(); } } }

 总结:使用Synchronized和Lock都能实现,而Lock的优势是可以精准唤醒,不像Synchronized的只能notifyAll()

 
原文地址:https://www.cnblogs.com/yayin/p/14193850.html