在 MyBatis 中,缓存机制用于提高数据库访问的性能,主要分为一级缓存和二级缓存。本文将详细介绍这两种缓存的区别、特点和使用场景。
一级缓存(Local Cache)
1. 作用域
- 一级缓存是
SqlSession
范围内的缓存。每个SqlSession
实例都有自己的一级缓存。
2. 生命周期
- 一级缓存的生命周期与
SqlSession
一致。当SqlSession
关闭时,一级缓存中的数据也会被清空。
3. 存储数据
- 一级缓存存储的是
SqlSession
中执行查询的结果。当同一SqlSession
中执行相同的查询时,MyBatis 会优先从一级缓存中获取数据,而不去查询数据库。
4. 使用场景
- 适合于在同一个
SqlSession
中频繁执行相同的查询。
// 在同一个 SqlSession 中
try (SqlSession sqlSession = sqlSessionFactory.openSession()) {
UserMapper userMapper = sqlSession.getMapper(UserMapper.class);
User user1 = userMapper.selectUser(1); // 查询数据库
User user2 = userMapper.selectUser(1); // 从一级缓存获取
}
二级缓存(Global Cache)
1. 作用域
- 二级缓存是跨
SqlSession
的缓存。它是整个应用程序范围内的缓存,可以被多个SqlSession
共享。
2. 生命周期
- 二级缓存的生命周期与 MyBatis 的
SqlSessionFactory
一致。即使SqlSession
关闭,二级缓存中的数据依然存在,直到应用程序结束或缓存被清空。
3. 存储数据
- 二级缓存存储的是从数据库中查询的结果,并且会根据 SQL 语句的唯一性来缓存数据。例如,如果多个不同的
SqlSession
查询相同的数据,二级缓存可以直接返回缓存的结果。
4. 使用场景
- 适合于在多个
SqlSession
之间共享数据,减少对数据库的重复查询。特别适合于读多写少的场景。
配置
要使用二级缓存,需要在 MyBatis 的配置文件中进行相关配置,如下所示:
<configuration>
<settings>
<setting name="cacheEnabled" value="true"/>
</settings>
<mappers>
<mapper resource="path/to/your/mapper.xml">
<cache/>
</mapper>
</mappers>
</configuration>
// 在不同的 SqlSession 中
try (SqlSession sqlSession1 = sqlSessionFactory.openSession()) {
UserMapper userMapper1 = sqlSession1.getMapper(UserMapper.class);
User user1 = userMapper1.selectUser(1); // 查询数据库
sqlSession1.commit();
}
try (SqlSession sqlSession2 = sqlSessionFactory.openSession()) {
UserMapper userMapper2 = sqlSession2.getMapper(UserMapper.class);
User user2 = userMapper2.selectUser(1); // 从二级缓存获取
sqlSession2.commit();
}
总结
- 一级缓存 是每个
SqlSession
的本地缓存,存储在内存中,适合于单个会话内的查询优化。 - 二级缓存 是跨会话的全局缓存,可以被多个
SqlSession
共享,适合于在应用中减少数据库访问。