• hutool工具实践-缓存


    简介

    依赖引入

    1. cn.hutool
    2. hutool-cache
    3. 5.8.17

    hutool工具既可以像上一章hutool工具实践-验证码-CSDN博客所说直接全部引入,也可以分模块引入

    使用示例

    先进先出

    1. /**
    2. * FIFO(first in first out) 先进先出策略。
    3. * 元素不停的加入缓存直到缓存满为止,当缓存满时,
    4. * 清理过期缓存对象,清理后依旧满则删除先入的缓存(链表首部对象)。
    5. *
    6. * 优点:简单快速 缺点:不灵活,不能保证最常用的对象总是被保留
    7. */
    8. @Test
    9. public void fifoCacheTest() {
    10. Cache fifoCache = CacheUtil.newFIFOCache(3);
    11. //加入元素,每个元素可以设置其过期时长,DateUnit.SECOND.getMillis()代表每秒对应的毫秒数,在此为3秒
    12. fifoCache.put("key1", "value1", DateUnit.SECOND.getMillis() * 3);
    13. fifoCache.put("key2", "value2", DateUnit.SECOND.getMillis() * 3);
    14. fifoCache.put("key3", "value3", DateUnit.SECOND.getMillis() * 3);
    15. //由于缓存容量只有3,当加入第四个元素的时候,根据FIFO规则,最先放入的对象将被移除
    16. fifoCache.put("key4", "value4", DateUnit.SECOND.getMillis() * 3);
    17. //value1为null
    18. String value1 = fifoCache.get("key1");
    19. System.out.println(value1);
    20. }

    过期时间缓存

    1. /**
    2. * 定时缓存,对被缓存的对象定义一个过期时间,当对象超过过期时间会被清理。
    3. * 此缓存没有容量限制,对象只有在过期后才会被移除。
    4. *
    5. * @throws InterruptedException
    6. */
    7. @Test
    8. public void timeCacheTest() throws InterruptedException {
    9. TimedCache timeCache = CacheUtil.newTimedCache(1000);
    10. timeCache.put("userName","张三", DateUnit.MINUTE.getMillis());
    11. TimeUnit.SECONDS.sleep(1);
    12. Object userName = timeCache.get("userName");
    13. System.out.println(userName);
    14. }

    如果用户在超时前调用了get(key)方法,会重头计算起始时间。举个例子,用户设置key1的超时时间5s,用户在4s的时候调用了get("key1"),此时超时时间重新计算,再过4s调用get("key1")方法值依旧存在。如果想避开这个机制,请调用get("key1", false)方法。

    此缓存没有容量限制,对象只有在过期后才会被移除,如果启动了定时器(schedulePrune方法),那会定时清理缓存中的过期值,但是如果不起动,那只有在get这个值得时候才检查过期并清理。不启动定时器带来的问题是:有些值如果长时间不访问,会占用缓存的空间

    最近最久未使用缓存

    1. /**
    2. * LRU (least recently used)最近最久未使用缓存。
    3. * 根据使用时间来判定对象是否被持续缓存,当对象被访问时放入缓存,当缓存满了,
    4. * 最久未被使用的对象将被移除。此缓存基于LinkedHashMap,因此当被缓存的对象每被访问一次,
    5. * 这个对象的key就到链表头部。这个算法简单并且非常快,他比FIFO有一个显著优势是经常使用的对象不太可能被移除缓存。
    6. * 缺点是当缓存满时,不能被很快的访问。
    7. */
    8. @Test
    9. public void lruCacheTest() {
    10. Cache lruCache = CacheUtil.newLRUCache(3);
    11. //通过实例化对象创建
    12. //LRUCache lruCache = new LRUCache(3);
    13. lruCache.put("key1", "value1", DateUnit.SECOND.getMillis() * 3);
    14. lruCache.put("key2", "value2", DateUnit.SECOND.getMillis() * 3);
    15. lruCache.put("key3", "value3", DateUnit.SECOND.getMillis() * 3);
    16. lruCache.get("key1");//使用时间推近
    17. lruCache.put("key4", "value4", DateUnit.SECOND.getMillis() * 3);
    18. //由于缓存容量只有3,当加入第四个元素的时候,根据LRU规则,最少使用的将被移除(2被移除)
    19. String value2 = lruCache.get("key"); //null
    20. }

    最少使用率策略

    1. /**
    2. * LFU(least frequently used) 最少使用率策略。
    3. * 根据使用次数来判定对象是否被持续缓存(使用率是通过访问次数计算),
    4. * 当缓存满时清理过期对象,清理后依旧满的情况下清除最少访问(访问计数最小)的对象并将其他对象的访问数减去这个最小访问数,
    5. * 以便新对象进入后可以公平计数。
    6. */
    7. @Test
    8. public void lfuCacheTest() {
    9. Cache lfuCache = CacheUtil.newLFUCache(3);
    10. //通过实例化对象创建
    11. //LFUCache lfuCache = new LFUCache(3);
    12. lfuCache.put("key1", "value1", DateUnit.SECOND.getMillis() * 3);
    13. lfuCache.get("key1");//使用次数+1
    14. lfuCache.put("key2", "value2", DateUnit.SECOND.getMillis() * 3);
    15. lfuCache.put("key3", "value3", DateUnit.SECOND.getMillis() * 3);
    16. lfuCache.put("key4", "value4", DateUnit.SECOND.getMillis() * 3);
    17. //由于缓存容量只有3,当加入第四个元素的时候,根据LFU规则,最少使用的将被移除(2,3被移除)
    18. String value2 = lfuCache.get("key2");//null
    19. String value3 = lfuCache.get("key3");//null
    20. }

    说明

    hutool的缓存策略均是基于缓存实现的,单独使用的机会较少(比较适合一些较为简单的单体项目),使用场景较多的情况是:结合redis等缓存技术做的多级缓存,提升系统性能

    源码浅析

    整个cache模块的核心接口在cn.hutool.cache.Cache,定义了缓存的相关方法

    cache的模板实现是AbstractCache,在该抽象模板中实现了大部分方法,定义了最关键的方法:

    putWithoutLock

    其中pruneCache清理缓存的方法由后续子类根据各自的特征实现
    getWithoutLock

    实践案例

    待补充

  • 相关阅读:
    Vue理解01
    Apache Doris (四十七): Doris表结构变更-Schema变更
    Vue2.7正式发布,终于可以在Vue2项目中使用Vue3的特性了,真香~
    IO面试题整理
    人工智能学习:NMIST数据分类识别-CNN网络(3)
    基于隐私保护计算的金融科技创新探索
    VS报错 The build tools for v141 (Platform Toolset = ‘v141‘) cannot be found.
    elasticsearch安装
    L48.linux命令每日一练 -- 第七章 Linux用户管理及用户信息查询命令 -- last、lastb和lastlog
    阿里云轻量应用服务器有月流量限制吗?
  • 原文地址:https://blog.csdn.net/qq_39203337/article/details/139500451