MyBatis缓存Cache源码分析

一、缓存接口介绍

MyBatis的一级缓存和二级缓存都是使用的Cache接口实现类,它的方法定义如下:

public interface Cache {

  String getId();

  void putObject(Object key, Object value);

  Object getObject(Object key);


  Object removeObject(Object key);


  void clear();


  int getSize();
  

  ReadWriteLock getReadWriteLock();

}

其实现类有:

其中除PerpetualCache以外,其他的Cache实现都是使用了装饰器模式,由底层的PerpetualCache完成实际的缓存,并在此基础上添加了其他功能。

BlockingCache/SynchronizedCache:通过在get/put方式中加锁,保证只有一个线程操作缓存

FifoCache、LruCache:当缓存到达上限时候,通过FIFO或者LRU(最早进入内存)策略删除缓存

ScheduledCache:在进行get/put/remove/getSize等操作前,判断缓存时间是否超过了设置的最长缓存时间(默认是一小时),如果是则清空缓存--即每隔一段时间清空一次缓存

SoftCache/WeakCache:通过JVM的软引用和弱引用来实现缓存,当JVM内存不足时,会自动清理掉这些缓存

PerpetualCache:使用一个HashMap作为缓存容器,实现了简单的缓存功能(从这里可以看到,这并不是一个线程安全的类),get和put等操作都是直接调用HaspMap的相应方法实现,实际定义如下:

public class PerpetualCache implements Cache {

  private final String id;

  private Map<Object, Object> cache = new HashMap<Object, Object>();

  public PerpetualCache(String id) {
    this.id = id;
  }

  @Override
  public String getId() {
    return id;
  }

  @Override
  public int getSize() {
    return cache.size();
  }

  @Override
  public void putObject(Object key, Object value) {
    cache.put(key, value);
  }

  @Override
  public Object getObject(Object key) {
    return cache.get(key);
  }

  @Override
  public Object removeObject(Object key) {
    return cache.remove(key);
  }

  @Override
  public void clear() {
    cache.clear();
  }

  @Override
  public ReadWriteLock getReadWriteLock() {
    return null;
  }

}

 

二、MyBatis执行器Executor简介

1、Executor接口及实现类介绍

MyBatis通过Executor执行增删查改等操作,接口代码如下:

public interface Executor {

  ResultHandler NO_RESULT_HANDLER = null;
  //修改操作
  int update(MappedStatement ms, Object parameter) throws SQLException;
  //普通查询
  <E> List<E> query(MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, CacheKey cacheKey, BoundSql boundSql) throws SQLException;  
  <E> List<E> query(MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler) throws SQLException;
  //通过游标查询
  <E> Cursor<E> queryCursor(MappedStatement ms, Object parameter, RowBounds rowBounds) throws SQLException;

  List<BatchResult> flushStatements() throws SQLException;

  void commit(boolean required) throws SQLException;

  void rollback(boolean required) throws SQLException;

  CacheKey createCacheKey(MappedStatement ms, Object parameterObject, RowBounds rowBounds, BoundSql boundSql);

  boolean isCached(MappedStatement ms, CacheKey key);

  void clearLocalCache();

  void deferLoad(MappedStatement ms, MetaObject resultObject, String property, CacheKey key, Class<?> targetType);

  Transaction getTransaction();

  void close(boolean forceRollback);

  boolean isClosed();

  void setExecutorWrapper(Executor executor);

}

其中定义了执行query、update(执行所有修改操作)的方法。MyBatis默认的Executor实现有:

CachingExecutor:实现二级缓存的Executor

BaseExecutor:是下面几个Executor的父类,使用了模版方法模式,对Executor的接口提供实现,其子类只需要实现doQuery、doQueryCursor、doFlushStatements、doUpdate来完成实际的数据库操作

SimpleExecutor:默认实现,简单的实现增删查改功能

BatchExecutor:BATCH 执行器将重用语句并执行批量更新

ReuseExecutor:对创建的Statement重复利用,其定义了一个Map<String, Stat

  • 4
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 4
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值