两个线程交替输出对应的数字字母(wait/notify)

先上代码:

public class Printer {

    private static final Object lock = new Object();

    private static int flg = 1;

    private static void start() {
        Thread t1 = new Thread(() -> {
            synchronized (lock) {
                try {
                    for (int i = 1; i <= 26; i++) {
                        if (flg != 1) {
                            lock.wait();
                        }
                        System.out.print(i);
                        flg = 2;
                        lock.notify();
                    }
                } catch (InterruptedException e) {
                    throw new RuntimeException(e);
                }
            }
        });
        Thread t2 = new Thread(() -> {
            synchronized (lock) {
                try {
                    for (char c = 'a'; c <= 'z'; c++) {
                        if (flg != 2) {
                            lock.wait();
                        }
                        System.out.print(c);
                        flg = 1;
                        lock.notify();
                    }
                } catch (InterruptedException e) {
                    throw new RuntimeException(e);
                }
            }
        });
        t1.start();
        t2.start();
    }

    public static void main(String[] args) {
        start();
    }
}

可以先参考: 多线程交替输出abc100次(wait/notify)-CSDN博客文章浏览阅读72次,点赞2次,收藏3次。那么我们接下来就需要实现Runnable接口了,使用Lambda表达式,首先不考虑计数,我们可以先设为无限循环while(true),然后抢锁,抢到之后,如果发现flag不对,就调wait释放锁,此线程就阻塞在wait那里,直到下次它再被唤醒,才会进入下一轮循环继续抢对象锁。设为while(true)是因为循环是不断重试的,有可能抢到锁但本轮并不应该是它输出,所以用了无限循环,这样也会一直交替打印下去,那我们怎么控制器打印次数呢?为此我引入了计数器,打完c之后加一,最后计数器的值小于一个固定值即可!https://blog.csdn.net/m0_60424152/article/details/136637002?spm=1001.2014.3001.5502       下面我讲讲和本题和链接题的异同之处,这次的题目同样需要标识位1和2。但是本题中for循环一定要放在内侧了,因为只需要打印1遍。我来描述下过程吧,我们抢到对象锁之后进入for循环,如果标识位正确,我们输出并切换标识位,之后唤醒等待的线程抢锁,而本线程则由于标识位不符,调用wait方法进入wait状态并释放锁,那另一个线程就一定可以抢到锁啦!

       调用wait后本线程一直在wait处“休息”,当其被唤醒之后,如果抢到锁会继续向下执行。底层原理浅显来说大致如下:操作系统中的monitor管程有几个指针,有一个指针指向抢到锁的线程,一个指针指向wait状态的线程队列,还有一个指向被阻塞住在抢锁的线程队列。我们调用wait后,抢到锁指针指向的线程会加入wait对应指针指向的队列进入wait状态,当期被notify后会进入抢锁队列抢锁,抢到锁之后的表现就是会从wait代码之后的位置开始执行!

 

  • 18
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值