博主原本以爲,《分佈式之數據庫和緩存雙寫一致性方案解析》,一文已經十分清晰。然而這一兩天,有人在微信上私聊我,以爲應該要採用html
先刪緩存,再更新數據庫,再刪緩存數據庫
這一方案做爲緩存更新策略,而不是先更新數據庫,再刪緩存。而且搬出了兩篇大佬的文章,《Cache Aside Pattern》,《緩存與數據庫不一致,咋辦?》,但願博主能加以說明。由於問的人太多了,因此纔有了這篇文章的誕生。緩存
在開始這篇文章以前,咱們先本身思考一下如下兩個更新策略微信
方案一分佈式
(1)刪緩存ide
(2)更數據庫線程
(3)刪緩存htm
方案二blog
(1)更數據庫get
(2)刪緩存
你們看下面的文章前,本身先思考一下,方案一的步驟(1)有沒有存在的必要?
先上一個結論:方案二存在的缺點,方案一所有存在,且方案一比方案二多一個步驟,因此應該選方案二。
下面,針對《Cache Aside Pattern》,《緩存與數據庫不一致,咋辦?》這兩篇文章提出的論點,提出小小的質疑。這兩篇文章認爲方案二不行的緣由,主要有如下兩點
(1)方案二在步驟(2),出現刪緩存失敗的狀況下,會出現數據不一致的情形,以下圖所示
Cache Aside Pattern方案存在什麼問題?
答:若是先操做數據庫,再淘汰緩存,在原子性被破壞時:
(1) 修改數據庫成功了
(2) 淘汰緩存失敗了
致使,數據庫與緩存的數據不一致
(2)方案二存在下面的主從同步,致使cache不一致問題,以下圖所示
大體流程就是,線程A寫,線程B讀,會有如下流程出現
(1)緩存恰好失效
(2)線程A寫入master數據庫,slave還沒同步
(3)線程B發現緩存失效,去slave讀到舊值
(4)線程A刪除緩存
(5)線程B把舊值放入緩存
然而你們發現了麼,這兩篇文章提出的反對意見,在該文做者本身所提出的方案一里頭也是存在的?
(1)針對刪緩存失敗問題 方案一的步驟(3)也會可能出現刪除緩存失敗問題,但是做者沒有加以詳細說明。
(2)針對數據不一致問題 線程A寫,線程B讀,會有如下流程出現
(1)線程A刪除緩存
(2)線程A寫入master數據庫,slave還沒同步
(3)線程B發現緩存失效,去slave讀到舊值
(4)線程A刪除緩存
(5)線程B把舊值放入緩存
綜上所述,咱們應該選擇方案二,而不是方案一。方案二存在的缺點,方案一所有存在,且方案一步驟上多了一步,增長了不穩定因素。
該文章只是糾正了一下目前流傳的觀點的正確性,並無針對任何人。技術的世界,只論技術。