緩存,究竟是淘汰,還是修改?
問:KV緩存都緩存了一些什麽數據?
答:
(1)樸素類型的數據,例如:int
(2)序列化後的對象,例如:User實體,本質是binary
(3)文本數據,例如:json或者html
(4)...
問:淘汰緩存中的這些數據,修改緩存中的這些數據,有什麽差別?
答:
(1)淘汰某個key,操作簡單,直接將key置為無效,但下一次該key的訪問會cache miss
(2)修改某個key的內容,邏輯相對復雜,但下一次該key的訪問仍會cache hit
可以看到,差異僅僅在於一次cache miss。
問:緩存中的value數據一般是怎麽修改的?
答:
(1)樸素類型的數據,直接set修改後的值即可
(2)序列化後的對象:一般需要先get數據,反序列化成對象,修改其中的成員,再序列化為binary,再set數據
(3)json或者html數據:一般也需要先get文本,parse成doom樹對象,修改相關元素,序列化為文本,再set數據
結論:對於對象類型,或者文本類型,修改緩存value的成本較高,一般選擇直接淘汰緩存。
問:對於樸素類型的數據,究竟應該修改緩存,還是淘汰緩存?
答:仍然視情況而定。
案例1:
假設,緩存裏存了某一個用戶uid=123的余額是money=100元,業務場景是,購買了一個商品pid=456。
分析:如果修改緩存,可能需要:
(1)去db查詢pid的價格是50元
(2)去db查詢活動的折扣是8折(商品實際價格是40元)
(3)去db查詢用戶的優惠券是10元(用戶實際要支付30元)
(4)從cache查詢get用戶的余額是100元
(5)計算出剩余余額是100 - 30 = 70
(6)到cache設置set用戶的余額是70
為了避免一次cache miss,需要額外增加若幹次db與cache的交互,得不償失。
結論:此時,應該淘汰緩存,而不是修改緩存。
案例2:
假設,緩存裏存了某一個用戶uid=123的余額是money=100元,業務場景是,需要扣減30元。
分析:如果修改緩存,需要:
(1)從cache查詢get用戶的余額是100元
(3)到cache設置set用戶的余額是70
為了避免一次cache miss,需要額外增加若幹次cache的交互,以及業務的計算,得不償失。
結論:此時,應該淘汰緩存,而不是修改緩存。
案例3:
假設,緩存裏存了某一個用戶uid=123的余額是money=100元,業務場景是,余額要變為70元。
分析:如果修改緩存,需要:
(1)到cache設置set用戶的余額是70
修改緩存成本很低。
結論:此時,可以選擇修改緩存。當然,如果選擇淘汰緩存,只會額外增加一次cache miss,成本也不高。
總結:
允許cache miss的KV緩存寫場景:
大部分情況,修改value成本會高於“增加一次cache miss”,因此應該淘汰緩存
如果還在糾結,總是淘汰緩存,問題也不大
作者:58沈劍
緩存,究竟是淘汰,還是修改?