我們知道,redis是乙個nosql資料庫,由於其資料都放在記憶體中,常常用來做快取。redis用作快取,肯定要和資料庫打交道。當然redis的應用場景還有很多,不光只用作快取。
在讀取快取方面,都是按照下圖的流程來進行業務操作。
但兄弟們有沒有想過如果資料庫中資料修改了,那麼快取的更新策略是什麼樣呢?我們現在就來討論這個問題。首先我們看看模擬查詢快取**。
定義乙個map集合作為快取,在實際生產中使用redis來做快取,實際上redis的底層結構也是map集合。
class
genericdaocached
extends
genericdao
//快取中沒有,查詢資料庫,然後將查詢結果放到快取中
dao.
queryone
(beanclass, sql, args)
; map.
put(key,value)
;return value;
}@override
public
intupdate
(string sql,object.
.. args)
}
首先分析一下,上述**可能會出現什麼問題?
首先,我們思考一下更新時,是先清除快取還是先更新資料庫?
先清快取,再更新資料庫
結果:造成查詢的值和資料庫中的值不一致
先更新資料庫,再清除快取
結果:造成a執行緒首次查詢和後續查詢得到不一致的結果,首次查詢得到 x=1,後續查詢發現已經清空了快取,需要去資料庫中查得 x=2
// 加寫鎖, 防止其它執行緒對快取讀取和更改
lock.
writelock()
.lock()
;try
return value;
}finally
}public
intupdate
(string sql, object.
.. params)
finally
}當然,實現快取更新策略還有很多方法,我們下回再述. . . . . .
快取更新策略
一般來說,快取有以下三種模式 cache aside更新模式 這種策略下,在併發寫的時候可能會出現髒資料的問題。read write through 更新模式 在read write through 更新模式中,應用程式只需要維護快取,資料庫的維護工作由快取 了。read through 模式就是在...
快取更新策略初探
這裡為什麼不讓更新操作在寫完資料庫之後,緊接著去把快取cache中的資料也修改了呢?主要是因為這樣做的話,就有2個寫操作的事件了,擔心在併發的情況下會導致髒資料,舉個例子 那麼 cache aside 模式就沒有髒資料問題了嗎?不是的,在極端情況下也可能會產生髒資料,比如 不過這種概率比上面一種概率...
Mysql 之 快取更新策略
業務角度,對於讀操作很少的,造成效能浪費 執行緒安全角度,容易產生資料髒讀 執行緒a更新了資料庫,執行緒b更新了資料庫,b更新了快取,a更新了快取 錯誤情況 請求a進行寫操作,刪除快取 請求b查詢發現快取不存在,讀取資料庫,寫入快取 請求a將資料寫入資料庫 解決方法 採用延時雙刪除法 在a寫入資料庫...