您好!
欢迎来到京东云开发者社区
登录
首页
博文
课程
大赛
工具
用户中心
开源
首页
博文
课程
大赛
工具
开源
更多
用户中心
开发者社区
>
博文
>
浅析本地缓存技术-Guava Cache
分享
打开微信扫码分享
点击前往QQ分享
点击前往微博分享
点击复制链接
浅析本地缓存技术-Guava Cache
自猿其说Tech
2023-06-09
IP归属:北京
11400浏览
计算机编程
# 1 引言 作为java开发工作者,相信大家对于guava这个工具包都不会太陌生,而对于本地缓存技术guava cache,大家在日常的工作开发中也都有所了解,接下来本文就从各个角度入手来对于Google提供的guava cache进行解析。 # 2 guava cache应用场景 本地缓存的数据读写都在一个进程内,相对与redis等分布式缓存,不需要网络传输的过程,访问速度很快,同时也受到JVM内存的制约,无法在数据量较多的场景下使用。 基于以上特点,guava cache的主要应用场景为以下几种: - 对于访问速度有较大要求 - 存储的数据不经常变化 - 数据量不大,占用内存较小 - 需要访问整个集合 - 能够容忍数据不是实时的 在这里guava cache被用于储存参数配置,也符合以上的应用场景条件。 ![](//img1.jcloudcs.com/developer.jdcloud.com/fb4a6e40-3189-46ae-a717-ff21d75f254720230423150707.png) # 3 guava cache的使用方式 guava cache位于com.google.common.cache包下,核心的类有两个,一个是CacheBuilder,是用来构建缓存的,另一个是Cache,也就是缓存容器,用来存放缓存数据的。 要使用guava cache,首先要引入maven依赖: ```xml <dependency> <groupId>com.google.guava</groupId> <artifactId>guava</artifactId> <version>18.0</version> </dependency> ``` 接下来写一个简单的示例: ```java Cache<String, String> localCache = CacheBuilder.newBuilder() .initialCapacity(5) .maximumSize(10) .concurrencyLevel(3) .expireAfterWrite(10, TimeUnit.SECONDS) .build(); ``` 以上示例实例化了一个本地缓存,接下来介绍一下初始化的各项参数的含义: initialCapacity:内部哈希表的最小容量,也就是cache的初始容量。 maximumSize:cache的最大缓存数。 concurrencyLevel:并发等级,也可以定义为同时操作缓存的线程数,由 ![](//img1.jcloudcs.com/developer.jdcloud.com/477e6f1a-4f28-4683-adac-83960e010f5920230423150824.png) 可以看出,这个线程数默认为4。 expireAfterWrite:缓存写入后刷新时间。 从缓存中获取数据调用的方法为get(K key, Callable<? extends V> loader)方法,此方法的含义是根据键key获取数据,若key不存在,则通过执行指定的Callable方法来构造缓存,示例代码如下所示: ```java Map<String, Dicdetail> dicDetailMap = ObLocateCache.locateConfigCache.get(key.toString(), new Callable<Map<String, Dicdetail>>() { @Override public Map<String, Dicdetail> call() throws Exception { return getConfigParameterFromMaster(baseDomain, KeyConstants.WMS5_LOCATE_MANUAL); } }); ``` 从cache中删除数据分为被动删除和主动删除两种: 1.被动删除: - 基于数据大小删除:LRU+FIFO - 基于过期时间删除:在指定时间内没有被访问 - 基于引用删除:通过weakKeys和weakValues方法指定Cache只保存对缓存记录key和value的弱引用。这样当没有其他强引用指向key和value时,key和value对象就会被垃圾回收器回收 2.主动删除: ```java //删除指定的key对应数据 cache.invalidate("s"); //将一批对应的数据删除 cache.invalidateAll(Arrays.asList("st","r","ing")); //全部删除 cache.invalidateAll(); ``` # 4 根据源码分析guava cache的存储原理 guava cache的数据结构跟ConcurrentHashMap类似,二者最基本的区别是ConcurrentMap会一直保存所有添加的元素,直至将添加的元素移除。相对地,guava cache为了限制内存占用,通常都设定为自动回收元素。 guava cache的核心类为LocalCache,LocalCache实现了ConcurrentMap接口。其中有一个Segment数组,如下所示 ![](//img1.jcloudcs.com/developer.jdcloud.com/7b33cd63-ac32-4744-9817-69cfe5a3023d20230423154145.png) 获取数据的方法源码如下图所示,可以看出guava cache的存储原理为由Segment数组加上ReferenceEntry链表加上AtomicReferenceArray数组组成的数据结构。 ![](//img1.jcloudcs.com/developer.jdcloud.com/8a43baba-b057-4eed-843f-9c43b3dd1be820230423154207.png) ![](//img1.jcloudcs.com/developer.jdcloud.com/0b35ec81-8183-4e09-b70d-51da642eb49920230423154222.png) ![](//img1.jcloudcs.com/developer.jdcloud.com/86133471-2c60-4228-a4fb-7813cdd3444320230423154257.png) 数据结构图如下所示: ![](//img1.jcloudcs.com/developer.jdcloud.com/9686f8d2-ee0a-42d7-b01d-16f9041d2a0920230423154326.png) Segement数组的长度决定了cache的并发数。每一个Segment都继承了ReentrantLock,使用了单独的锁,对Segment的写操作需要先拿到锁。写操作部分源码如下所示: ![](//img1.jcloudcs.com/developer.jdcloud.com/f9479f90-b175-414f-a186-fa4c876db70b20230423154343.png) ![](//img1.jcloudcs.com/developer.jdcloud.com/da1f5c3c-27f3-4fd2-a777-9811b7ddb2a120230423154428.png) # 5 总结 本文简要叙述了guava cache的应用场景以及简单的使用方式,通过源码对于guava cache的存储原理以及简单的读写方法进行了介绍。相信通过阅读本文,能够对于常见的guava cache有一个大致的认知。 ------------ 自猿其说Tech-JDL京东物流技术与数据智能部 **作者:王辰玮**
原创文章,需联系作者,授权转载
上一篇:Python自动化测试的配置层实现方式对标与落地
下一篇:TiDB简述及TiKV的数据结构与存储
相关文章
Taro小程序跨端开发入门实战
Flutter For Web实践
配运基础数据缓存瘦身实践
自猿其说Tech
文章数
426
阅读量
2149964
作者其他文章
01
深入JDK中的Optional
本文将从Optional所解决的问题开始,逐层解剖,由浅入深,文中会出现Optioanl方法之间的对比,实践,误用情况分析,优缺点等。与大家一起,对这项Java8中的新特性,进行理解和深入。
01
Taro小程序跨端开发入门实战
为了让小程序开发更简单,更高效,我们采用 Taro 作为首选框架,我们将使用 Taro 的实践经验整理了出来,主要内容围绕着什么是 Taro,为什么用 Taro,以及 Taro 如何使用(正确使用的姿势),还有 Taro 背后的一些设计思想来进行展开,让大家能够对 Taro 有个完整的认识。
01
Flutter For Web实践
Flutter For Web 已经发布一年多时间,它的发布意味着我们可以真正地使用一套代码、一套资源部署整个大前端系统(包括:iOS、Android、Web)。渠道研发组经过一段时间的探索,使用Flutter For Web技术开发了移动端可视化编程平台—Flutter乐高,在这里希望和大家分享下使用Flutter For Web实践过程和踩坑实践
01
配运基础数据缓存瘦身实践
在基础数据的常规能力当中,数据的存取是最基础也是最重要的能力,为了整体提高数据的读取能力,缓存技术在基础数据的场景中得到了广泛的使用,下面会重点展示一下配运组近期针对数据缓存做的瘦身实践。
自猿其说Tech
文章数
426
阅读量
2149964
作者其他文章
01
深入JDK中的Optional
01
Taro小程序跨端开发入门实战
01
Flutter For Web实践
01
配运基础数据缓存瘦身实践
添加企业微信
获取1V1专业服务
扫码关注
京东云开发者公众号