SynchronousQueue详解「建议收藏」

SynchronousQueue详解「建议收藏」SynchronousQueue是BlockingQueue的一种,所以SynchronousQueue是线程安全的。SynchronousQueue和其他的BlockingQueue不同的是SynchronousQueue的capacity是0。即SynchronousQueue不存储任何元素。也就是说SynchronousQueue的每一次insert操作,必须等待其他线性的remove操作。而每一个remove操作也必须等待其他线程的insert操作。这种特性可以让我们想起了Exchanger

大家好,又见面了,我是你们的朋友全栈君。

文章目录

SynchronousQueue详解

简介

SynchronousQueue是BlockingQueue的一种,所以SynchronousQueue是线程安全的。SynchronousQueue和其他的BlockingQueue不同的是SynchronousQueue的capacity是0。即SynchronousQueue不存储任何元素。

也就是说SynchronousQueue的每一次insert操作,必须等待其他线性的remove操作。而每一个remove操作也必须等待其他线程的insert操作。

这种特性可以让我们想起了Exchanger。和Exchanger不同的是,使用SynchronousQueue可以在两个线程中传递同一个对象。一个线程放对象,另外一个线程取对象。

举例说明

我们举一个多线程中传递对象的例子。还是举生产者消费者的例子,在生产者中我们创建一个对象,在消费者中我们取出这个对象。先看一下用CountDownLatch该怎么做:

    @Test
    public void useCountdownLatch() throws InterruptedException { 
   
        ExecutorService executor = Executors.newFixedThreadPool(2);
        AtomicReference<Object> atomicReference= new AtomicReference<>();
        CountDownLatch countDownLatch = new CountDownLatch(1);

        Runnable producer = () -> { 
   
            Object object=new Object();
            atomicReference.set(object);
            log.info("produced {}",object);
            countDownLatch.countDown();
        };

        Runnable consumer = () -> { 
   
            try { 
   
                countDownLatch.await();
                Object object = atomicReference.get();
                log.info("consumed {}",object);
            } catch (InterruptedException ex) { 
   
                log.error(ex.getMessage(),ex);
            }
        };

        executor.submit(producer);
        executor.submit(consumer);

        executor.awaitTermination(50000, TimeUnit.MILLISECONDS);
        executor.shutdown();
    }

上例中,我们使用AtomicReference来存储要传递的对象,并且定义了一个型号量为1的CountDownLatch。

在producer中,我们存储对象,并且countDown。

在consumer中,我们await,然后取出对象。

输出结果:

[pool-1-thread-1] INFO com.flydean.SynchronousQueueUsage - produced java.lang.Object@683d1b4b
[pool-1-thread-2] INFO com.flydean.SynchronousQueueUsage - consumed java.lang.Object@683d1b4b

可以看到传入和输出了同一个对象。

上面的例子我们也可以用SynchronousQueue来改写:

    @Test
    public void useSynchronousQueue() throws InterruptedException { 
   
        ExecutorService executor = Executors.newFixedThreadPool(2);
        SynchronousQueue<Object> synchronousQueue=new SynchronousQueue<>();

        Runnable producer = () -> { 
   
            Object object=new Object();
            try { 
   
                synchronousQueue.put(object);
            } catch (InterruptedException ex) { 
   
                log.error(ex.getMessage(),ex);
            }
            log.info("produced {}",object);
        };

        Runnable consumer = () -> { 
   
            try { 
   
                Object object = synchronousQueue.take();
                log.info("consumed {}",object);
            } catch (InterruptedException ex) { 
   
                log.error(ex.getMessage(),ex);
            }
        };

        executor.submit(producer);
        executor.submit(consumer);

        executor.awaitTermination(50000, TimeUnit.MILLISECONDS);
        executor.shutdown();
    }

上面的例子中,如果我们使用synchronousQueue,则可以不用手动同步,也不需要额外的存储。

总结

如果我们需要在代码中用到这种线程中传递对象的情况,那么使用synchronousQueue吧。

本文的例子https://github.com/ddean2009/learn-java-collections

更多精彩内容且看:

欢迎关注我的公众号:程序那些事,更多精彩等着您!
更多内容请访问 www.flydean.com

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/152133.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • clover默认引导mac(clover win10引导)

    搞定Clover引导的Win&Mac双系统系统迁移至SSD作者:毛毛卷日期:2018-07-20字体大小:小中大从发完贴到现在总算搞定了,具体操作记录如下:由于当年折腾双系统的时候就经历了很多波折而且一般是默认启动MAC而我却是WIN10所以本身的要求和实现方法就有点特殊因此最终并没有偷懒用分区克隆的方法还是按部就班的进行首先把自己提的几个问题回答一下吧首先大概试了A…

    2022年4月11日
    38
  • 到小公司去

    到小公司去

    2022年1月22日
    51
  • 域名ssl证书怎么弄_nginx配置https证书

    域名ssl证书怎么弄_nginx配置https证书越来越多的第三方接入需要使用https了,很多时候不止到证书到那里免费申请,申请后怎么配置。免费证书和收费证书主要的差别有几点免费证书收费证书支持绑定域名数少支持绑定域名数多无保险费用有保险费用一年需要更换两年或三年可选颁发机构少更多的颁发机构证书免费申请的几个大平台阿里云腾讯云…

    2022年10月1日
    1
  • 【机器学习算法】线性回归算法

    【机器学习算法】线性回归算法文章目录线性回归回归问题回归和分类预测未来机器学习实现预测的流程线性方程权值调整最简单的回归问题——线性回归问题利用线性回归进行预测的极速入门线性回归的算法原理拟合线性回归算法的数学解析1.假设函数的数学表达式解析线性回归回归问题线性方程偏差度量权值更新回归问题两百年前,与达尔文同时代的统计学家高尔顿在研究父代与子代的身高关系时,发现一种“趋中效应”:如果父代身高高于平均值,则子代具有更高概率比他父亲要矮,简单来说就是身高回归平均值。“回归”一词也由此而来。在回归的世界里,万物的发展轨

    2022年8月21日
    5
  • hive修改字段类型语句_hive的数据类型

    hive修改字段类型语句_hive的数据类型altertable表名changecolumn原字段名现字段名字段类型

    2025年8月27日
    5
  • Android应用程序启动过程源代码分析(4)

    Android应用程序启动过程源代码分析(4)

    2021年8月13日
    52

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号