当前位置: 首页 > news >正文

ConcurrentSkipListSet和ConcurrentSkipListMap分析以及总结Set

ConcurrentSkipListSet和ConcurrentSkipListMap分析以及总结Set

ConcurrentSkipListSet怎么实现线程安全

跳表结构

跳表是一种概率型数据结构,由多个层级的链表组成,每个元素在不同的层中出现的概率是固定的。这种结构使得在平均情况下,插入、删除和查找操作的时间复杂度为 (O(\log n))。

2. 原子操作

ConcurrentSkipListSet 的内部实现依赖于 java.util.concurrent.atomic 包中的原子类,如 AtomicIntegerAtomicReference。这允许在并发环境中安全地更新节点和指针。

3. 锁分段技术

跳表的每个节点都有一个前向指针(即指向下一个节点),在进行插入和删除时,ConcurrentSkipListSet 会使用一种锁分段策略。它对每个节点的更新操作仅锁定该节点及其前后节点,而不是整个数据结构。这种局部性减少了锁竞争,提高了并发性能。

4. CAS(Compare-And-Swap)

ConcurrentSkipListSet 在插入和删除元素时,使用 CAS 操作来更新节点的指针。通过原子性地更新指针,避免了传统锁机制所带来的开销。

5. 遍历操作

在遍历时,ConcurrentSkipListSet 允许其他线程对集合进行并发修改。这是通过复制当前状态的快照(snapshot)来实现的,确保遍历的线程能够看到一致的视图。

1. ConcurrentSkipListMap 与 ConcurrentSkipListSet

JDK中包含两个与SkipList相关的数据结构,分别是ConcurrentSkipListSet和ConcurrentSkipListMap,二者均为并发容器,一个是Set实现一个是Map实现。 而ConcurrentSkipListSet内部实际上包含一个ConcurrentSkipListMap,其将元素作为ConcurrentSkipListMap的key存放,所以本质上也以ConcurrentSkipListMap作为底层实现。这里将主要分析ConcurrentSkipListMap的源代码。

2. 与ConcurrentHashMap对比

  1. ConcurrentSkipListMap与ConcurrentHashMap都是线程安全的并发容器,可以应用于并发读写场景。

  2. ConcurrentHashMap底层基于哈希,ConcurrentSkipListMap底层基于跳表结构,而跳表本身是有序的,所以ConcurrentSkipListMap也是有序的。

3. ConcurrentSkipListMap采用的无锁删除算法

基础的算法基于 HM linked ordered set algorithm (Tim Harris, "A pragmatic implementation of non-blocking linked lists")的变种。它的基本思想是在删除节点时标记待删除结点的下一个结点,来避免并发的插入冲突。作者也提到另一种方案是使用AtomicMarkedReference,但是作者认为AtomicMarkedReference不够高效, 直接使用CAS操作更加高效。

具体在删除时,采用的是类似懒删除的策略,如果一个结点的value为null,则认为它已经被逻辑删除

假设待删除结点为n,b为它的前驱结点,f为它的后继结点

第一步CAS设置n的value为null,此时该结点已经被逻辑删除,插入、查找等操作将会忽略该结点。

第二步CAS设置n的后继结点为一个Marker结点(value指向自己),此时任何操作都不会再其后继续添加结点。

第三步CAS设置n的前驱结点b指向其后继结点f,完成删除。

在这个过程中,如果第一步失败,则会进行重试。第二步或第三步失败也不会影响其他操作,因为该结点value已经被设置成null,其他操作会忽略该结点,相当于该结点已经被删除。并且其他操作内部有帮助删除操作,会检查value已经被设定成null的结点,帮助其完成删除的第二步和第三步。

4. 源码分析

在ConcurrentSkipListMap源代码的基础上,对主要的查询、插入、删除等操作进行分析,并增加了详细的代码注释,帮助理解ConcurrentSkipListMap的源代码。

Set大汇总(横屏观看)

Set有序性线程安全底层实现关键接口特点
HashSetHashMap简单
LinkedHashSetLinkedHashMap插入顺序
TreeSetNavigableMapNavigableSet自然顺序
CopyOnWriteArraySetCopyOnWriteArrayList插入顺序,读写分离
ConcurrentSkipListSetConcurrentSkipListMapNavigableSet自然顺序

从中我们可以发现一些规律:

(1)除了HashSet其它Set都是有序的;

(2)实现了NavigableSet或者SortedSet接口的都是自然顺序的;

(3)使用并发安全的集合实现的Set也是并发安全的;

(4)TreeSet虽然不是全部都是使用的TreeMap实现的,但其实都是跟TreeMap相关的(TreeMap的子Map中组合了TreeMap);

(5)ConcurrentSkipListSet虽然不是全部都是使用的ConcurrentSkipListMap实现的,但其实都是跟ConcurrentSkipListMap相关的(ConcurrentNavigableMap为ConcurrentSkipListMap的具体实现);


http://www.mrgr.cn/news/62159.html

相关文章:

  • 【HarmonyOS-ArkTS语言】计算器的实现【合集】
  • Unity 2d描边基于SpriteRender,高性能的描边解决方案
  • 高等数学学习笔记 ☞ 导数的基础知识
  • LInux单机安装Redis
  • 设计模式 行为型 策略模式(Strategy Pattern)与 常见技术框架应用 解析
  • 使用 Three.js 创建动态粒子效果
  • 魔法伤害--是谁偷走了我的0
  • NEEP-EN2-2020-Section1
  • 100种算法【Python版】第28篇——扩展欧几里得算法
  • 【Linux】--- 开发工具篇:yum、vim、gcc、g++、gdb、make、makefile
  • highcharts的datalabels标签格式化
  • 【计网】网络协议栈学习总结 --- 浏览器上输入网址域名后点击回车,到底发生了什么?
  • 通过不当变更导致 PostgreSQL 翻车的案例分析与防范
  • Python金色流星雨(完整代码)
  • ubuntu 挂载 新 硬盘 ext3
  • 高等数学(数二专题)
  • 在Windows下通过pip安装Selenium
  • lenovo联想小新 潮7000-14AST(81GE)笔记本原厂Win10系统镜像安装包下载
  • 软件评测第二期
  • 练习LabVIEW第二十七题
  • window11使用wsl2安装Ubuntu22.04
  • 易至狂欢购车季火热开启,EV3青春版打造年轻一代出行新选择
  • 如何安装自动化测试工具katalon?
  • LC20. 有效的括号
  • Java AQS CountDownLatch 总结
  • 图文并茂教你如何发布自己的NPM包(GitHub Packages npm 包发布)