Google Guava Cache LoadingCache 基本使用

一. 添加依赖

复制代码
<dependency>
    <groupId>com.google.guava</groupId>
    <artifactId>guava</artifactId>
    <version>27.1-jre</version>
</dependency>

二. 创建CacheLoader

复制代码
LoadingCache<Long, String> cache = CacheBuilder.newBuilder()
                //缓存池大小,在缓存项接近该大小时, Guava开始回收旧的缓存项
                .maximumSize(GUAVA_CACHE_SIZE)
                //设置过期策略
                .expireAfterWrite(10, TimeUnit.MINUTES)
                //设置刷新策略
                .refreshAfterWrite(10, TimeUnit.MINUTES)
                //移除监听器,缓存项被移除时会触发
                .removalListener(new RemovalListener <Long, String>() {
                    @Override
                    public void onRemoval(RemovalNotification<Long, String> rn) {
                        //执行逻辑操作
                    }
                })
                //开启Guava Cache的统计功能
                .recordStats()
                .build(cacheLoader);

 CacheLoader<String, String> cacheLoader = new CacheLoader<String, String>() {
            //expire后或第一次加载时 调用
            @Override
            public String load(String key) throws Exception {
                return "";
            }

            //refresh时调用
            @Nullable
            @Override
            public ListenableFuture<String> reload(String key, HostInfo oldValue) throws Exception {
                return super.reload(key, oldValue);
            }
        };

三.配置

1.expireAfterAccess(long, TimeUnit)

缓存项在给定时间内没有被读/写访问,则回收。请注意这种缓存的回收顺序和基于大小回收一样,再次加载key,调用CacheLoader的load方法。

2.expireAfterWrite(long, TimeUnit)

缓存项在给定时间内没有被写访问(创建或覆盖),则回收。如果认为缓存数据总是在固定时候后变得陈旧不可用,这种回收方式是可取的,再次加载key,调用CacheLoader的load方法。

3.refreshAfterAccess(long duration, TimeUnit unit)

缓存项在给定时间内没有被读/写访问,则刷新,再次加载key,调用CacheLoader的reload方法。

4.refreshAfterWrite(long duration, TimeUnit unit)

缓存项在给定时间内没有被写访问(创建或覆盖),则刷新,再次加载key,调用CacheLoader的reload方法。

因为load是同步加载,reload是异步加载。

expire load的优点:失效后下次查询是实时的数据。

缺点:如果大量缓存同时失效,查询耗时会比较长。

refresh reload的优点:reload是异步的,查询会很快返回。

缺点:当数据到达失效时间时,会先返回上次的value,当reload完成后再会返回实时的数据,数据实时性低于load。

综合使用

复制代码
CacheBuilder.newBuilder().expireAfterWrite(timeOut, TimeUnit.MINUTES).expireAfterWrite(timeOut+ expireTime, TimeUnit.MINUTES);

timeOut内访问数据会使用reload加载数据,在超过timeOut+ expireTime内访问数据会使用load加载数据。

四.Caffeine

https://www.oschina.net/p/ben-manes-caffeine?hmsr=aladdin1e1

Caffeine 是基于Java 8的高性能,接近最佳的缓存库。 Caffeine使用Google Guava启发的API提供内存缓存。

性能上优于Guava Cache,使用方法类似。

作者:摩V羯座

链接:https://www.jianshu.com/p/41c683242b33

来源:简书

著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

相关推荐
架构师沉默1 小时前
设计多租户 SaaS 系统,如何做到数据隔离 & 资源配额?
java·后端·架构
Java中文社群3 小时前
重要:Java25正式发布(长期支持版)!
java·后端·面试
每天进步一点_JL4 小时前
JVM 类加载:双亲委派机制
java·后端
用户298698530144 小时前
Java HTML 转 Word 完整指南
java·后端
渣哥4 小时前
原来公平锁和非公平锁差别这么大
java
渣哥5 小时前
99% 的人没搞懂:Semaphore 到底是干啥的?
java
J2K5 小时前
JDK都25了,你还没用过ZGC?那真得补补课了
java·jvm·后端
kfyty7255 小时前
不依赖第三方,不销毁重建,loveqq 框架如何原生实现动态线程池?
java·架构
isysc16 小时前
面了一个校招生,竟然说我是老古董
java·后端·面试
道可到10 小时前
Java 反射现代实践速查表(JDK 11+/17+)
java