最新一个高并发项目中需要大量使用sync.map,为了更好的评估sync.map对的cpu和内存影响,深入探究一下sync.map的原理,最好总结,为后面的选型做好准备.

1、sync.map的数据结构

相比与Java中的CurrentHashMap来说sync.map的实现简单了许多.一句话总结sync.map使用了写时复制的技术实现了高并发的map.
我们先来看看sync.map的数据结构类图.这里就不贴代码,最好结合代码再来看这张图.

从在这里,我们可以看到sync.map封装了真正value的指针.当key存在的时候,那么可以直接通过value的unsafe指针做原子替换,做到无锁替换值的效果.当key不存在的时候,就相对比较复杂.我们再来看看Stroe函数的流程.

2、Store函数

  • 从图中我们可以看到蓝色的路径是无锁路径,即当key在写表与读表同时存在时,那么直接拿到entry然后替换真正value的指针即可
  • 当key的值在读表中不存在、或者key的值只在读表中存在(即entry的指针指向expunge)时.那么就会开始加锁,并把记录往写表的里面写.
  • 这里用到我们熟悉的双重判断
  • 如果在最开始的时候写入一大波不同key,那么会一直加锁,但只要key被插入过一次,且没被删除,那么就一直不用加锁.这个跟java有一定的区别
  • 通过expunge不用加锁就可以知道写表中是否存在这个key,这个点记住,因为后面的函数会多次用这个字段来判断key在写表中是否存在
  • 可以理解读表是作为一层缓存的存在,写的时候加锁写真正的map.读的时候从缓存读,缓存没有再击穿进去读.如果一直在写新的key,但一直在读sync.map中不存在的key,也会导致一直加锁

3、Delete函数

  • 删除的关键动作就是找到key,并把entry中指向的值置为nil,所以这里也存在找key的动作
  • 在找key的时候,如果key不存在,那么一定要加锁去写表中找
  • 这里有两个关键信息,就是读表删除的时候,是将entry中的value指向nil.到写表中删除的时候,是直接删除这个key

4、Load函数

  • 读出的流程跟删除的流程差不多,这里就不再累述

5、总结

  • go的sync.map的实现主要是用了读写两张表的方式实现的,在实现上面比java的简单很多.对于那种不是很频繁插入key的场景比较合适.不像java是使用分桶key实现
  • 在这个意义上,可以理解读表是写表的一个缓存,当读取的次数达到len(写表)的数量时,那么就刷一次缓存到读表.当写表为空的时候,需要复制一份写表的数据出来.如果此时数据比较多的话,那么也会消费比较多的时间片.

sync.map原理解析相关推荐

  1. Golang sync.Map 原理(两个map实现 读写分离、适用读多写少场景)

    参考: 由浅入深聊聊Golang的sync.Map 通过对源码的逐行分析,清晰易懂 Golang sync.Map原理 通过向 sync.Map 中增删改查来介绍sync.Map的底层原理 Golan ...

  2. Golang sync.Map原理

    原生map的"先天不足" 对于已经初始化了的原生map,我们可以尽情地对其进行并发读: package mainimport ("fmt""math/ ...

  3. sync.Map低层工作原理详解

    sync.Map低层工作原理详解 目录 为什么需要sync.Map?适合什么场景? sync.Map内部实现基本原理及结构体分析 sync.Map低层工作原理 1. 为什么需要sync.Map?适合什 ...

  4. singleflight包原理解析

    转载地址:https://silenceper.com/blog/202003/singleflight/ singleflight 包主要是用来做并发控制,常见的比如防止 缓存击穿 ,我们来模拟一下 ...

  5. 【重识云原生】第六章容器基础6.4.5.3节——Deployment实现原理解析

    <重识云原生系列>专题索引: 第一章--不谋全局不足以谋一域 第二章计算第1节--计算虚拟化技术总述 第二章计算第2节--主流虚拟化技术之VMare ESXi 第二章计算第3节--主流虚拟 ...

  6. Android 广播实现原理解析

    Android 广播实现原理解析 前言 Android四大组件中的BroadcastReceiver,在我们实际工作中被频繁的使用,我们可以利用系统的开机广播,网络状态改变的广播等等实现我们的业务逻辑 ...

  7. 时序数据库-2-[IoTDB]的原理解析

    清华自研时间序列数据库Apache IoTDB原理解析 时序数据库 Apache-IoTDB 源码解析之前言(一) 时序数据库 Apache-IoTDB 源码解析之系统架构(二) 时序数据库 Apac ...

  8. jetpack compose原理解析

    目录 jetpack compose原理解析 jetpack compse 声明式ui开发 原理分析 整体框架介绍 compose LayoutNode布局介绍 @Composeable注解实现细节 ...

  9. Spark Shuffle原理解析

    Spark Shuffle原理解析 一:到底什么是Shuffle? Shuffle中文翻译为"洗牌",需要Shuffle的关键性原因是某种具有共同特征的数据需要最终汇聚到一个计算节 ...

最新文章

  1. 干掉visio,这个画图神器真的绝了!!!
  2. 清华校庆正当时,智能小车决赛日
  3. 数据存储之 SQLite 数据库操作(二)
  4. 从给定的N个正数中选取若干个数之和最接近M
  5. 哪种修复redis未授权访问漏洞的方法是相对不安全的_关于Linux挖矿、DDOS等应急事件处置方法...
  6. 新编标准日本语 第26课 课文
  7. SpringMVC请求后台地址URL没有.*的几种实现方式
  8. ubuntu16.04下Caffe绘制训练过程的loss和accuracy曲线
  9. 设计模式(1):工厂模式
  10. 异常处理 Exceptions
  11. 公用Laravel 5框架与公用库架构
  12. SEO网站搜索引擎优化软件
  13. 使用 k3d 来运行极狐GitLab Runner
  14. 计算机英语ppt答辩,急求英语答辩PPT范文
  15. dw自动滚动图片_Dreamweaver实现滚动图片文字
  16. NFT Insider #49:YGG学员总量突破20000名,《南华早报》在The Sandbox中构建香港天星码头
  17. 有没有讲python模块的书_python - 模块,包
  18. android 当服务器
  19. 外行怎么快速林java_我自学编程,只为月薪过万,就这么简单!(外行也可看)...
  20. git统计提交代码量

热门文章

  1. 微服务网关soul,这篇值得你拥有
  2. 10个可爱的外国互动型网站
  3. 豆瓣上《特权和寻租的经济学》的书评
  4. 【抽象代数】第一章 代数系统《抽象代数极简教程》/ By 禅与计算机程序设计艺术ChatGPT
  5. npm ERR! code ENOENT npm ERR! syscall open npm ERR! path E:\jd\pro1\ka-mrm-jd_intern\package.json np
  6. [转]北京ATM跨行取款学问多(2008年07月26日)
  7. 未被定义的 “智能座舱”,如何将产业化进行到底
  8. 这大概是你见过最全面的 Python 重点了
  9. mysql 空间索引_Mysql空间索引
  10. Arduino ESP8266固件bin升级四种方法