日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

缓存级别与缓存更新问题

發(fā)布時(shí)間:2025/3/21 编程问答 19 豆豆
生活随笔 收集整理的這篇文章主要介紹了 缓存级别与缓存更新问题 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

緩存失效問(wèn)題被認(rèn)為是計(jì)算機(jī)科學(xué)中最難的兩件事之一,這篇文章來(lái)自翻譯,內(nèi)容主要包括緩存級(jí)別與緩存更新常見(jiàn)的幾種模式。

緩存應(yīng)用模式

常見(jiàn)緩存應(yīng)用模式

緩存常用來(lái)加快頁(yè)面的加載速度,減少服務(wù)器或數(shù)據(jù)庫(kù)服務(wù)的負(fù)載。緩存應(yīng)用的常見(jiàn)模式如上圖所示:

  • 檢索緩存,嘗試查找之前相同請(qǐng)求的執(zhí)行結(jié)果,如果找到了則返回,省去了重新執(zhí)行的步驟;
  • 如果緩存未命中,則重新執(zhí)行計(jì)算邏輯并將結(jié)果保存至緩存;
  • 數(shù)據(jù)庫(kù)常常得益于對(duì)均勻分布的數(shù)據(jù)的讀寫(xiě),但是熱點(diǎn)數(shù)據(jù)使得這種均勻被打破,從而出現(xiàn)了系統(tǒng)瓶頸。通過(guò)數(shù)據(jù)庫(kù)服務(wù)前置緩存服務(wù),可以有效吸收不均勻的負(fù)載和抵擋流量高峰。

    緩存級(jí)別

    緩存級(jí)別關(guān)注的問(wèn)題是在什么時(shí)候做緩存(When)以及在什么地方做緩存(Where),下面介紹幾種常見(jiàn)的緩存級(jí)別。

    客戶端緩存

    緩存可以存儲(chǔ)在客戶端(操作系統(tǒng)或?yàn)g覽器、服務(wù)端、或者是獨(dú)立的緩存系統(tǒng)中。

    CDN緩存

    CDN也可以被認(rèn)為是一種緩存。

    Web服務(wù)器緩存

    反向代理或者像Varnish這樣的緩存服務(wù)可以直接保存靜態(tài)的或動(dòng)態(tài)的緩存內(nèi)容。Web服務(wù)器也可以緩存請(qǐng)求直接響應(yīng)客戶端從而避免請(qǐng)求再次觸達(dá)應(yīng)用。

    數(shù)據(jù)庫(kù)緩存

    我們的數(shù)據(jù)庫(kù)服務(wù)在默認(rèn)的配置或者稍微針對(duì)通用場(chǎng)景進(jìn)行優(yōu)化的情況下通常包含不同級(jí)別的緩存,針對(duì)特定的使用場(chǎng)景進(jìn)行適當(dāng)?shù)恼{(diào)整可以進(jìn)一步提高性能。

    應(yīng)用緩存

    像Memcached和Redis這種內(nèi)存key-value緩存服務(wù),通常是置于應(yīng)用和數(shù)據(jù)庫(kù)服務(wù)之間,因?yàn)閿?shù)據(jù)存儲(chǔ)在內(nèi)存中,因此這要比將數(shù)據(jù)存儲(chǔ)在磁盤(pán)的數(shù)據(jù)庫(kù)要快的多。但是內(nèi)存與磁盤(pán)相比往往受限于空間,因此類(lèi)似LRU(Least Recently Used)這種緩存淘汰算法應(yīng)運(yùn)而生,他們將相對(duì)較少訪問(wèn)的”冷”數(shù)據(jù)從內(nèi)存置換出來(lái)將訪問(wèn)頻率較高的“熱”數(shù)據(jù)放入內(nèi)存(將內(nèi)存的使用價(jià)值最大化,譯者注)。

    Redis還有很多其他的功能,包括:

    • 持久化選項(xiàng);
    • 內(nèi)建數(shù)據(jù)結(jié)構(gòu)(如sets、lists);

    下面是針對(duì)數(shù)據(jù)庫(kù)查詢級(jí)別對(duì)象級(jí)別的一般緩存:

    • 行級(jí)緩存;
    • 查詢級(jí)別緩存;
    • 完全序列化的緩存;
    • 渲染后的HTML緩存;

    值得一提的是,我們通常要避免文件級(jí)別的緩存,因?yàn)榛谖募木彺娉3ky于擴(kuò)展和維護(hù)。

    查詢級(jí)別緩存:

    每當(dāng)我們查詢數(shù)據(jù)庫(kù)的時(shí)候,將查詢(比如SQL)進(jìn)行hash并作為key和查詢結(jié)果關(guān)聯(lián)存儲(chǔ),這種方法會(huì)遇到緩存過(guò)期的問(wèn)題:

    • 對(duì)于復(fù)雜的查詢很難刪除緩存的結(jié)果;
    • 緩存粒度較大,如果查詢結(jié)果中只有丁點(diǎn)數(shù)據(jù)被更新,則整個(gè)查詢都要過(guò)期;

    對(duì)象級(jí)別緩存:

    對(duì)象級(jí)別緩存是將數(shù)據(jù)看做對(duì)象:

    • 如果數(shù)據(jù)被修改則將數(shù)據(jù)從緩存中移除;
    • 使用異步的任務(wù)來(lái)更新緩存;

    對(duì)象級(jí)別的緩存建議的使用場(chǎng)景:

    • 用戶會(huì)話;
    • 渲染后的頁(yè)面;
    • 活動(dòng)流;
    • 用戶圖形數(shù)據(jù);

    緩存更新問(wèn)題

    因?yàn)閮?nèi)存受限于空間緩存只能存儲(chǔ)有限的數(shù)據(jù),因此我們需要決定在我們的應(yīng)用場(chǎng)景中,使用何種緩存更新策略,下面介紹幾種常見(jiàn)的模式。

    Cache-Aside

    Cache-Aside模式

    應(yīng)用負(fù)責(zé)基于存儲(chǔ)讀寫(xiě)數(shù)據(jù),緩存不直接和存儲(chǔ)打交道,應(yīng)用的行為如下:

  • 檢索緩存,緩存沒(méi)有命中;
  • 從數(shù)據(jù)庫(kù)加載數(shù)據(jù);
  • 將數(shù)據(jù)更新至緩存;
  • 返回結(jié)果;
  • 代碼示例如下:

    1 2 3 4 5 6 7 def get_user(self, user_id): ????user = cache.get("user.{0}", user_id) ????if user is None: ????????user = db.query("SELECT * FROM users WHERE user_id = {0}", user_id) ????????if user is not None: ????????????cache.set(key, json.dumps(user)) ????return user

    這種模式的缺點(diǎn)如下:Memcached通常被應(yīng)用于這種方式,這種模式對(duì)于接下來(lái)的數(shù)據(jù)讀取將非???#xff0c;Cache-Aside也叫做延遲加載,只有需要的數(shù)據(jù)被緩存,避免不需要的數(shù)據(jù)占用緩存空間。

    • 每次緩存沒(méi)命中都增加系統(tǒng)之間的交互,這將會(huì)增加響應(yīng)延遲;
    • 當(dāng)對(duì)應(yīng)數(shù)據(jù)庫(kù)中的數(shù)據(jù)被更新之后將出現(xiàn)臟數(shù)據(jù)問(wèn)題,這個(gè)問(wèn)題可以通過(guò)設(shè)置過(guò)期時(shí)間(TTL)來(lái)緩解,當(dāng)時(shí)間過(guò)期將發(fā)生強(qiáng)制更新緩存;
    • 當(dāng)一個(gè)節(jié)點(diǎn)壞了之后,新的節(jié)點(diǎn)代替舊的節(jié)點(diǎn),這個(gè)時(shí)候?qū)⒊霈F(xiàn)大量的緩存穿透問(wèn)題;

    Write-Though

    Write-Though模式

    應(yīng)用將緩存作為主要存儲(chǔ),讀寫(xiě)都直接和緩存打交道,緩存負(fù)責(zé)基于存儲(chǔ)進(jìn)行讀寫(xiě):

  • 應(yīng)用基于緩存添加或刪除記錄;
  • 緩存同步地將記錄寫(xiě)入存儲(chǔ);
  • 返回;
  • 應(yīng)用代碼示例:

    1 set_user(12345, {"foo":"bar"})

    緩存代碼如下:

    1 2 3 def set_user(user_id, values): ????user = db.query("UPDATE Users WHERE id = {0}", user_id, values) ????cache.set(user_id, user)

    Write-Though對(duì)于所有的寫(xiě)操作都是比較慢的,但是對(duì)于讀來(lái)說(shuō)很快,用戶通常需要容忍寫(xiě)延遲,但是不會(huì)出現(xiàn)臟數(shù)據(jù)。

    這種模式的缺點(diǎn)如下:

    • 由于failure或者scaling帶來(lái)的新增節(jié)點(diǎn)的時(shí)候,新增節(jié)點(diǎn)在下次更新數(shù)據(jù)之前將沒(méi)有數(shù)據(jù),這個(gè)問(wèn)題可以結(jié)合Cache-Aside模式來(lái)緩解;
    • 對(duì)于很多寫(xiě)入的數(shù)據(jù)將永遠(yuǎn)不會(huì)讀取到,這個(gè)問(wèn)題可以通過(guò)設(shè)置過(guò)期時(shí)間解決;

    Write-Behind(Write-Back)

    Write-Behind模式

    在這種模式下,應(yīng)用的行為如:

  • 直接讀寫(xiě)緩存;
  • 寫(xiě)操作通知任務(wù)來(lái)異步進(jìn)行更新;
  • 這種模式的缺點(diǎn)如下:

    • 如果在數(shù)據(jù)被更新到存儲(chǔ)之前緩存掛了,則數(shù)據(jù)將會(huì)丟失;
    • 實(shí)現(xiàn)起來(lái)比Write-Though和Cache-Aside模式更為復(fù)雜;

    Refresh-Ahead

    Refresh-Ahead模式

    我們可以配置緩存自動(dòng)在最近訪問(wèn)的數(shù)據(jù)過(guò)期之前更新它們,如果可以準(zhǔn)確預(yù)測(cè)將要訪問(wèn)的數(shù)據(jù),Refresh-Ahead模式可以有效地減少讀寫(xiě)的延遲。

    這種模式的缺點(diǎn)如下:

    • 如果預(yù)測(cè)數(shù)據(jù)不準(zhǔn)確,則比不做什么更有損性能;

    緩存的缺點(diǎn)

    一種解決方案通常會(huì)帶來(lái)一些問(wèn)題,我們來(lái)看看引入緩存帶來(lái)的問(wèn)題:

    • 緩存的引入帶來(lái)了一致性問(wèn)題,我們需要處理緩存中的數(shù)據(jù)與原數(shù)據(jù)不一致的問(wèn)題;
    • 緩存的引入增加了軟件架構(gòu)的復(fù)雜性;;
    • 緩存過(guò)期是個(gè)難題,這個(gè)問(wèn)題主要體現(xiàn)在何時(shí)更新緩存上;

    擴(kuò)展閱讀

    • From cache to in-memory data grid
    • Scalable system design patterns
    • Introduction to architecting systems for scale
    • Scalability, availability, stability, patterns
    • Scalability
    • AWS ElastiCache strategies
    • Wikipedia
    原文出處:?Float_Luuu
    from:?http://www.importnew.com/23967.html

    總結(jié)

    以上是生活随笔為你收集整理的缓存级别与缓存更新问题的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

    如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。