V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
monetto
V2EX  ›  Java

求助, 为什么 Array 阻塞队列和 Linked 阻塞队列的锁不一样?

  •  
  •   monetto · 2019-09-17 14:46:05 +08:00 · 3197 次点击
    这是一个创建于 1905 天前的主题,其中的信息可能已经有所发展或是发生改变。

    ArrayBlockingQueue 的锁是读写不分离的。 而 LinkedBlockingQueue 的锁是读写分离的。这样就可以同时读和写了。 为什么要这么设计? 网上搜了一大圈答案都不太满意。

    这里还有对 ArrayBlockingQueue 进行改造的。 https://blog.csdn.net/icepigeon314/article/details/93792519 貌似改造后效果还更好了, 为啥 Java 不一开始就这么设计?

    3 条回复    2019-09-19 08:18:01 +08:00
    HelloAmadeus
        1
    HelloAmadeus  
       2019-09-17 15:30:39 +08:00 via iPhone
    从数据结构上理解哈。数据 queue 有一个 index,读写都得改这个 index,列表 queue 读改表头,写改表尾,互不干扰。
    guyeu
        2
    guyeu  
       2019-09-17 15:58:58 +08:00
    一楼说的对了一半,ArrayBlockingQueue 有两个 index,一个是 takeIndex 用于读,一个是 putIndex 用于写,从 index 的角度,可以做成读写分离,问题在于还有一个整数 count,记录队列里元素的数量,不管是读还是写都要修改这个整数的值,所以不管读还是写都要锁一下。
    LinkedBlockingQueue 用 AtomicInteger 来记录元素数量,这个读写不分离的锁被隐藏在了 AtomicInteger 里,锁的粒度更细了。而 ArrayBlockingQueue 在读写元素时的运算量很小,所以没必要用太细粒度的锁。
    monetto
        3
    monetto  
    OP
       2019-09-19 08:18:01 +08:00
    @HelloAmadeus
    @guyeu
    感谢感谢~~才看到
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   1091 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 22ms · UTC 19:05 · PVG 03:05 · LAX 11:05 · JFK 14:05
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.