自定义(java)的缓存实现

参照别人写的一个完全自定义的缓存实现,即不用任何第三方的组件来实现某种对象的内存缓存。

场景是:对一个用户查询方法做缓存,以用户id为 key,用户本身为 value,当以相同的id查询用户的时候,直接从缓存中返回结果,否则更新缓存。用户查询服务还支持 reload 缓存(即清空缓存)。

首先定义一个实体类:用户类(User),具备基本的 id,name ,password属性,且具备 getter 和 setter 方法

 

清单 1. User.java

<p>package cache;</p><p>import java.io.Serializable;</p><p>public class User implements Serializable {
 /**
  * 
  */
 private static final long serialVersionUID = 1L;
 private Integer id;
 private String name;
 private String password;</p><p> public User() {</p><p> }</p><p> public User(int id, String name, String password) {
  this.id = id;
  this.name = name;
  this.password = password;
 }</p><p> public Integer getId() {
  return id;
 }</p><p> public String getName() {
  return name;
 }</p><p> public String getPassword() {
  return password;
 }</p><p> public void setId(Integer id) {
  this.id = id;
 }</p><p> public void setName(String name) {
  this.name = name;
 }</p><p> public void setPassword(String password) {
  this.password = password;
 }</p><p>}</p>

然后定义一个缓存管理器,这个管理器负责实现缓存逻辑,支持对象的增加、修改和删除,支持值对象的泛型。如下:

清单 2. MyCacheManager.java

<p>package cache;</p><p>import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;</p><p>public class MyCacheManager<T> {
 private Map<String, T> cache = new ConcurrentHashMap<String, T>();</p><p> // 获取缓存中的记录
 public T getValue(Object key) {
  return cache.get(key);
 }</p><p> // 根据key更新缓存中的记录
 public void addOrUpdateCache(String key, T value) {
  cache.put(key, value);
 }</p><p> // 根据 key 来删除缓存中的一条记录
 public void evictCache(String key) {
  if (cache.containsKey(key)) {
   cache.remove(key);
  }
 }</p><p> // 清空缓存中的所有记录
 public void evictCache() {
  cache.clear();
 }
}
</p>


现在我们有了实体类和一个缓存管理器,还需要一个提供用户查询的服务类,此服务类使用缓存管理器来支持用户查询缓存(如果需要从数据库中获取数据的话,请自己增加DAO层,并将一下构造体中的数据删除),如下:

清单 3. UserService.java

<p>package cache;</p><p>import java.util.HashMap;
import java.util.Map;</p><p>public class UserService {
 private MyCacheManager<User> cache;</p><p> private static Map<String, User> users = new HashMap<String, User>();</p><p> public UserService() {
  cache = new MyCacheManager<User>();
  users.put("41", new User(41, "fan01", "123"));
  users.put("42", new User(42, "fan02", "123"));
  users.put("43", new User(43, "fan03", "123"));
 }</p><p> // 根据id,获取用户信息
 public User getUserById(Integer id) {
  User userCache = cache.getValue(id.toString());
  if(null != userCache){
   System.out.println("+++++++++++++++++++++++++++++++++++++++cache!!!");
   return userCache;
  }
  User result = users.get(id.toString());
  if(null != result){
   cache.addOrUpdateCache(id.toString(), result);
   System.out.println("+++++++++++++++++++++++++++++++++++++++数据库!!!");
  }
  return result;
 }
 
 // 根据id,清除缓存中的信息
 public void evictCache(Integer key){
  cache.evictCache(key.toString());
 }
 
 // 清除缓存中的信息
 public void evictCache(){
  cache.evictCache();
 }
}
</p>

好的,一切OK,终于到测试环节了,写个测试类,如下:
清单 4. TestUserCache.java

package cache;

public class TestUserCache {
	static UserService userService = new UserService();

	public static void main(String[] args) {

		// 开始查询账号
		// 第一次查询,应该是数据库查询
		userService.getUserById(41);

		// 第二次查询,应该直接从缓存返回
		userService.getUserById(41);

		// 清除缓存中的用户信息
		userService.evictCache();
		
		System.out.println("清除缓存后,再次查询用户信息..........");
		
		// 第一次查询,应该是数据库查询
		userService.getUserById(41);
		
		// 第二次查询,应该直接从缓存返回
		userService.getUserById(41);

	}
}

最后附上一张图片:

 


 

 

 

 

 

 

 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值