发帖    主题    评论    推荐    标签    作者    订阅    查搜    注册   登陆   关注
 
面向对象 设计模式 领域驱动设计 企业架构 框架 开发教程 微服务 大数据 扩展性 并发编程 事件驱动 分布式 SOA

caffeine: Java 8高性能缓存库包

    
2017-04-06 22:38
赞助商链接

Caffeine提供一个in-memory缓存,类似Google Guava的API,在Guava基础上提高了各种体验。

通常我们对缓存有两种操作,存入缓存和更新缓存:

Cache<K, V> cache = ...

public V read(K key) {
V result = cache.getIfPresent(key);
if (result == null) {
result = readFromDatabase(key);
cache.put(key, result);
}

return result;
}

public void write(K key, V value) {
writeToDatabase(key, value);
// force the value to be re-read from
// the database on next read(key) invocation
cache.invalidate(key);
};

这是一种get-if absent compute-put模式,也就是如果缓存没有该元素,则从数据库获得放入缓存。

假设有两个线程T1和T2,第一个调用缓存读取,第二个缓存写入,两个线程同时运行时,缓存中获取的值可能不是刚刚写入数据库值,也就是脏数据。

使用Guava测试代码如下:

AtomicReference<Integer> db = new AtomicReference<>(1);

LoadingCache<String, Integer> c = CacheBuilder.newBuilder().build(
new CacheLoader<String, Integer>() {
public Integer load(String key) {
println("Reading from db ...");
Integer v = db.get();
sleep(1000L);
println("Read from db: " + v);
return v;
}
}
);

Thread t1 = new Thread(() -> {
Integer g = c.get("k");
println("Got from cache: " + g);
});

Thread t2 = new Thread(() -> {
sleep(500L);
println("Writing to db ...");
db.set(2);
println("Wrote to db");
c.invalidate("k");
println("Invalidated cached");
});

t1.start();
t2.start();

t1.join();
t2.join();

System.out.println();
println("In cache: " + c.get("k"));


得到结果:

Thread-1 (123): Reading from db ...
Thread-2 (612): Writing to db ...
Thread-2 (612): Wrote to db
Thread-2 (613): Invalidated cached
Thread-1 (1142): Read from db: 1
Thread-1 (1145): Got from cache: 1

main (1146): In cache: 1


尽管缓存已经invalidate,但是缓存还是能获得K的值。

而如果使用Caffeine.newBuilder(),能得到正确结果:

Thread-1 (122): Reading from db ...
Thread-2 (624): Writing to db ...
Thread-2 (624): Wrote to db
Thread-1 (1146): Read from db: 1
Thread-2 (1146): Invalidated cached
Thread-1 (1146): Got from cache: 1

main (1147): Reading from db ...
main (2149): Read from db: 2
main (2149): In cache: 2

这获得了正确及俄国,是因为Caffeine 有一个 key-scoped锁,当调用cache.get时,指定键key的锁会一直保留到其值被计算加载完成。

GitHub - ben-manes/caffeine: A high performance ca

缓存     

赞助商链接

赞助商链接

返回顶部

移动版 关于本站 使用帮助 联系管理员 最佳分辨率1366x768
OpenSource JIVEJDON Powered by JdonFramework Code © 2002-20 jdon.com