Don't talk about martial arts (manual dog head): The interviewer gave me a few multi-threaded code questions and asked me to tear it up, and I pulled the cold from my heart~~~

Article Directory



Preface

Chestnut Flower Falling Chanahu

The hostess is so beautiful
Insert picture description here



Two threads, one thread prints odd numbers, one thread prints even numbers

ReentrantLock + Condition to achieve

public class Main {


    private static Lock lock = new ReentrantLock();
    static Condition c1 = lock.newCondition();
    static Condition c2 = lock.newCondition();

	//数字
    static volatile int num = 1;

    public static void main(String[] args) {


		//线程A
        new Thread(() -> {
            lock.lock();
            try{
                while (true) {
                	//如果是奇数
                    if (num % 2 == 1) {
                        System.out.println(Thread.currentThread().getName() + "打印奇数:\t" + num);
                        num++;
                        c2.signal();
                        c1.await();
                    }
                }
            }catch(Exception e){
                e.printStackTrace();
            }finally{
                lock.unlock();
            }
        },"A").start();

		//线程B
        new Thread(() -> {
            lock.lock();
            try{
                while (true) {
                	//如果是偶数
                    if (num % 2 == 0) {
                        System.out.println(Thread.currentThread().getName() + "打印偶数:\t" + num);
                        num++;
                        TimeUnit.SECONDS.sleep(1);
                        c1.signal();
                        c2.await();
                    }
                }
            }catch(Exception e){
                e.printStackTrace();
            }finally{
                lock.unlock();
            }
        },"B").start();

    }


}
Insert picture description here



Three threads print ABC

public class Main {

    private static int state = 0;
    private static final Lock lock = new ReentrantLock();

    public static void main(String[] args) {

        //打印A
        Thread a = new Thread(() -> {
            while (true) {
                lock.lock();
                try{
                    if (state % 3 == 0) {
                        System.out.print("A");
                        state++;
                    }
                }catch(Exception e){
                    e.printStackTrace();
                }finally{
                    lock.unlock();
                }
            }
        });

        //打印B
        Thread b = new Thread(() -> {
            while (true) {
                lock.lock();
                try{
                    if (state % 3 == 1) {
                        System.out.print("B");
                        state++;
                    }
                }catch(Exception e){
                    e.printStackTrace();
                }finally{
                    lock.unlock();
                }
            }
        });

        //打印C
        Thread c  = new Thread(() -> {
            while (true) {
                lock.lock();
                try{
                    if (state % 3 == 2) {
                        System.out.println("C");
                        TimeUnit.SECONDS.sleep(1);
                        state++;
                    }
                }catch(Exception e){
                    e.printStackTrace();
                }finally{
                    lock.unlock();
                }
            }
        });

        a.start();
        b.start();
        c.start();
    }

}
Insert picture description here



Thread prints A5 times, B10 times, C15 times

public class Test01 {


    private int number = 1;
    private static Lock lock = new ReentrantLock();
    static Condition c1 = lock.newCondition();
    static Condition c2 = lock.newCondition();
    static Condition c3 = lock.newCondition();


    public void printNum(int num,Condition st,Condition start,int currentNum,int futureNum) {
        lock.lock();
        try{
            while (number != currentNum) {
                st.await();
            }
            for (int i = 1; i <= num; i++) {
                System.out.println(Thread.currentThread().getName() + "\t" + i);
            }
            number = futureNum;
            start.signal();
        }catch(Exception e){
            e.printStackTrace();
        }finally{
            lock.unlock();
        }

    }


    public static void main(String[] args) {
        Test01 test01 = new Test01();

        new Thread(() -> {
            for (int i = 0; i < 2; i++) {
                test01.printNum(5,c1,c2,1,2);
            }
        },"AAA").start();

        new Thread(() -> {
            for (int i = 0; i < 2; i++) {
                test01.printNum(10,c2,c3,2,3);
            }
        },"BBB").start();

        new Thread(() -> {
            for (int i = 0; i < 2; i++) {
                test01.printNum(15,c3,c1,3,1);
            }
        },"CCC").start();
    }
}
Insert picture description here
The picture is not finished



Create water molecules

Realize two methods to generate a water molecule H2O, one method outputs an O, and the other method outputs an H. The water molecule needs to be composed of 2 H and 1 O.

public class Main {


    private static ReentrantLock lock = new ReentrantLock();
    private static Condition c1 = lock.newCondition();
    private static Condition c2 = lock.newCondition();
    private static AtomicInteger num = new AtomicInteger(1);

    public static void printH2() {
        lock.lock();
        try{
            System.out.print("H");
            if (num.intValue() % 2 == 0) {
                c2.signal();
                c1.await();
            }else {
                num.incrementAndGet();
                printH2();
            }
        }catch(Exception e){
            e.printStackTrace();
        }finally{
            lock.unlock();
        }
    }

    public static void printO() {
        lock.lock();
        try{
            System.out.println("O");
            TimeUnit.SECONDS.sleep(1);
            num.incrementAndGet();
            c1.signal();
            c2.await();
        }catch(Exception e){
            e.printStackTrace();
        }finally{
            lock.unlock();
        }
    }

    public static void main(String[] args) {

        new Thread(() -> {
            while (true) {
                printH2();
            }
        },"1").start();

        new Thread(() -> {
            while (true) {
                printO();
            }
        },"2").start();
    }



}
Insert picture description here



Producers and consumers block the regular version

public class Test01 {


    private Lock lock = new ReentrantLock();
    private Condition condition = lock.newCondition();
    private volatile int num = 0;

    //生产者
    public void produce() {
        lock.lock();
        try{
            //如果不等于0,那么就不去生产
            while (num != 0) {
                condition.await();
            }
            //生产
            num++;
            System.out.println(Thread.currentThread().getName() + "\t生产:" + num);
            //唤醒
            condition.signal();
        }catch(Exception e){
            e.printStackTrace();
        }finally{
            lock.unlock();
        }
    }


    //消费者
    public void consumer() {
        lock.lock();
        try{
            //如果恒等于0,那么就不能去消费
            while (num == 0) {
                condition.await();
            }
            //消费
            num--;
            System.out.println(Thread.currentThread().getName() + "\t消费:" + num);
            TimeUnit.SECONDS.sleep(1);
            //唤醒
            condition.signal();
        }catch(Exception e){
            e.printStackTrace();
        }finally{
            lock.unlock();
        }
    }

    public static void main(String[] args) {

        Test01 test = new Test01();

        new Thread(() -> {
            while (true) {
                test.produce();
            }
        },"A").start();

        new Thread(() -> {
            while (true) {
                test.consumer();
            }
        },"B").start();
    }
}
Insert picture description here



Producer, consumer blocking queue version

public class Test01 {


    public static void main(String[] args) {
        //将阻塞队列容量初始化为5
        MySource source = new MySource(new ArrayBlockingQueue<>(5));

        new Thread(() -> {
            System.out.println(Thread.currentThread().getName() + "\t 生产线程启动");
            try {
                source.myProduct();
            }catch (Exception e) {
                e.printStackTrace();
            }
        },"Product").start();

        new Thread(() -> {
            System.out.println(Thread.currentThread().getName() + "\t 消费线程启动");
            System.out.println();
            try {
                source.myConsumer();
            }catch (Exception e) {
                e.printStackTrace();
            }
        },"Consumer").start();


		//5秒后退出
        try {
            TimeUnit.SECONDS.sleep(5);
        }catch (Exception e) {
            e.printStackTrace();
        }

        System.out.println();
        System.out.println("时间到,结束!");
        source.stop();
    }
}


class MySource {
    private volatile boolean FLAG = true; // 默认开启 生产+消费

    private AtomicInteger atomicInteger = new AtomicInteger();

    //阻塞队列
    BlockingQueue<String> blockingQueue = null;

    public MySource(BlockingQueue<String> blockingQueue) {
        this.blockingQueue = blockingQueue;
    }


    //生产者
    public void myProduct() throws Exception {
        String data = null;
        boolean retValue;
        while (FLAG) {
            data = atomicInteger.incrementAndGet() + "";
            //添加到阻塞队列,默认过期时间为2秒,offer方法返回的是 boolean值
            retValue = blockingQueue.offer(data,2L, TimeUnit.SECONDS);
            if (retValue) {
                System.out.println(Thread.currentThread().getName() + "\t 插入队列成功" + data);
            }else {
                System.out.println(Thread.currentThread().getName() + "\t 插入队列失败" + data);
            }
            TimeUnit.SECONDS.sleep(1);
        }
        System.out.println(Thread.currentThread().getName() + "\t 停止生产");
    }

    //消费者
    public void myConsumer() throws Exception {
        String result = null;
        while (FLAG) {
            //两秒钟从队列中取不到就不放弃不取了
            result = blockingQueue.poll(2L,TimeUnit.SECONDS);
            //如果从队列中拿不到值,或者为 "",
            if (null == result || "".equals(result)) {
                FLAG = false;
                System.out.println(Thread.currentThread().getName() + "\t 超时,消费退出");
                return;
            }

            System.out.println(Thread.currentThread().getName() + "\t 消费队列成功" + result);
        }
        System.out.println(Thread.currentThread().getName() + "\t 停止消费");
    }

    public void stop() {
        this.FLAG = false;
    }
}
Insert picture description here

At last

I am a master of CRUD sketching , and I will continue to update blog posts that are beneficial to everyone in the future. I look forward to your attention! ! !

It’s not easy to create. If this blog post is helpful to you, I hope you guys canOne-click three consecutive!, Thanks for your support, see you next time~~~

Share outline

Dachang Interview Questions Column


Java From Entry to Grave Learning Route Catalog Index


Open Source Crawler Example Tutorial Catalog Index

For more exciting content to share, please click Hello World (●'◡'●)



Recently, CSDN has an exclusive production event, which is the following "Java Full Stack Knowledge Graph". The route planning is very detailed, and the
size is that the 870mm x 560mmfriends can follow the above process for systematic learning. Don't just find the book yourself. Book chaotic learning, we must study systematically and regularly, so that the foundation is the most solid. In our industry, "The foundation is not strong, the earth is shaking" is especially obvious, remember! ! !

Finally, if you are interested, you can buy it as appropriate to pave the way for your future! ! !


Insert picture description here