Mybatis-二級快取
MyBatis的二級快取
二級快取是SqlSessionFactory級別,通過同一個SqlSessionFactory建立的SqlSession查詢的結果會被 快取;此後若再次執行相同的查詢語句,結果就會從快取中獲取
二級快取開啟的條件:
a>在核心配置檔案中,設定全域性配置屬性cacheEnabled="true",預設為true,不需要設定
b>在對映檔案中設定標籤
c>二級快取必須在SqlSession關閉或提交之後有效
d>查詢的資料所轉換的實體類型別必須實現序列化的介面
使二級快取失效的情況:
兩次查詢之間執行了任意的增刪改,會使一級和二級快取同時失效
開啟二級快取:
第一步核心配置檔案設定全域性配置屬性cacheEnabled="true",預設為true,不需要設定
第二步配置檔案:
第三步查詢的資料所轉換的實體類型別必須實現序列化的介面:
舉例:
不同的sqlSession查詢方法相同,引數相同,兩次查詢期間執行一次sqlSession關閉
檢視結果:
可以看到不同sqlSession只執行了一次sql語句,說明二級快取成功
不同的sqlSession查詢方法相同,引數相同,兩次查詢期間執行任意一次增刪改操作
@Test public void selectEmpById(){ SqlSession session = MybatisUtils.getSqlSession(); EmpMapper mapper1 = session.getMapper(EmpMapper.class); Emp emp1 = mapper1.selectEmpById(1); System.out.println("emp"+emp1); int i = mapper1.insertEmp(new Emp(12, "張氏", 29, "男", "[email protected]")); System.out.println("添加了"+i+"條資料"); SqlSession sqlSession = MybatisUtils.getSqlSession(); EmpMapper mapper = sqlSession.getMapper(EmpMapper.class); Emp emp = mapper.selectEmpById(1); System.out.println(emp); }
檢視結果:
可以看到不同sqlSession執行同一方法期間執行了任意一次增刪改操作,執行力兩次sql語句,說明此時二級快取失效
二級快取的相關配置
在mapper配置檔案中新增的cache標籤可以設定一些屬性:
eviction屬性:快取回收策略
LRU(Least Recently Used) – 最近最少使用的:移除最長時間不被使用的物件。
FIFO(First in First out) – 先進先出:按物件進入快取的順序來移除它們。
SOFT – 軟引用:移除基於垃圾回收器狀態和軟引用規則的物件。
WEAK – 弱引用:更積極地移除基於垃圾收集器狀態和弱引用規則的物件。 預設的是 LRU。
flushInterval屬性:重新整理間隔,單位毫秒
預設情況是不設定,也就是沒有重新整理間隔,快取僅僅呼叫語句時重新整理
size屬性:引用數目,正整數
代表快取最多可以儲存多少個物件,太大容易導致記憶體溢位
readOnly屬性:只讀,true/false
true:只讀快取;會給所有呼叫者返回快取物件的相同例項。因此這些物件不能被修改。這提供了 很重要的效能優勢。
false:讀寫快取;會返回快取物件的拷貝(通過序列化)。這會慢一些,但是安全,因此預設是 false。
MyBatis快取查詢的順序
先查詢二級快取,因為二級快取中可能會有其他程式已經查出來的資料,可以拿來直接使用。
如果二級快取沒有命中,再查詢一級快取
如果一級快取也沒有命中,則查詢資料庫
SqlSession關閉之後,一級快取中的資料會寫入二級快取