我正在实现一个简单的缓存,缓存存储为AtomicReference.private AtomicReferenceMapString, String cacheData;应该从数据库表中填充(延迟)缓存对象.我提供了一种方法来将缓存数据返回给调用者,但如果数据为空(即...
我正在实现一个简单的缓存,缓存存储为AtomicReference.
private AtomicReference<Map<String, String>> cacheData;
应该从数据库表中填充(延迟)缓存对象.
我提供了一种方法来将缓存数据返回给调用者,但如果数据为空(即未加载),则代码需要从数据库加载数据.为避免同步我想到使用compareAndSet()方法:
public Object getCacheData() {
cacheData.compareAndSet(null, getDataFromDatabase()); // atomic reload only if data not set!
return Collections.unmodifiableMap(cacheData.get());
}
以这种方式使用compareAndSet是否可以.将数据库调用作为原子动作的一部分?是否比同步方法更好/更差?
非常感谢任何建议..
解决方法:
您没有达到预期的行为.这个表达式:
cacheData.compareAndSet(null, getDataFromDatabase())
将始终首先调用getDataFromDatabase().这意味着数据是否被缓存无关紧要.如果是,您仍然会调用数据库,但会丢弃结果.缓存正在运行,但性能同样差.
请考虑一下:
if(cacheData.get() == null) {
cacheData.compareAndSet(null, unmodifiableMap(getDataFromDatabase()));
}
return cacheData.get());
它并不完美(仍然可以在开始时多次调用getDataFromDatabase()),但是会在预期的时间内工作.此外,我之前移动了Collections.unmodifiableMap(),这样您就不必反复包装相同的地图.
这使我们更简单的实现(不需要同步或AtomicReference):
private volatile Map<String, String> cacheData;
if(cacheData == null) {
cacheData = unmodifiableMap(getDataFromDatabase());
}
return cacheData;
本文标题为:java – 使用AtomicReference.compareAndSet来设置对数据库调用结果的引用是否合适?
- 解决Spring在Thread中注入Bean无效的问题 2022-10-30
- Java中如何将json字符串转换成map/list 2023-02-19
- Java多线程(单例模式,阻塞队列,定时器,线程池)详解 2023-05-24
- JavaWeb Servlet生命周期细枝末节处深究 2023-06-10
- 阿里面试Nacos配置中心交互模型是push还是pull原理解析 2023-03-15
- 基于Java开发实现ATM系统 2023-04-12
- Springboot详解RocketMQ实现消息发送与接收流程 2023-01-29
- 一文带你了解Spring中@Enable开头注解的使用 2023-05-19
- Java实现基础银行ATM系统 2022-11-16
- java Stream流常见操作方法(反射,类加载器,类加载,反射) 2023-02-10