每當我們討論快取時,總是會對如下幾個詞比較熟悉,
write-back, write-through, write-around
似乎,快取主要是為「寫」設計的,其實這是錯誤的理解,寫從快取中獲得的好處是非常有限的,快取主要是為「讀」服務的。
之所以我們要順帶提一下,在乙個快取系統中,如何處理寫的順序,是因為,在寫的過程中,需要動態的更新快取(否則就會產生資料不一致性的問題),以及後端主存。這三個詞都是用來表示如何處理寫更新的。就是用什麼方式來處理寫。
在乙個有快取的層次結構中,如何理解快取是為「讀」服務的?這涉及到讀請求的處理序列。對於每乙個讀請求,我們都會用如下的操作序列去處理它:
1. 在快取中查詢請求對應的資料
a. 如果找到,則直接返回給客戶
b. 如果沒找到,則把請求的資料讀入快取(更新快取),然後把資料返回給客戶
既然快取主要是為讀服務的(後面的文章,我們會討論,用什麼方式來改善寫的效能),那麼為了提高讀的效能,或者說減少讀的響應時間,我們就要提高快取的命中率,減少快取的miss 率。這也是我們快取演算法設計的目標。
那麼我們來想想,在設計快取時,我們應該從哪幾方面考慮來達到這個快取的設計目標呢?根據我們上面提到的讀請求的操作序列,我們可以從如下幾個方面來思考:
1. 我們應該盡量多的用有用的資料填滿快取。也就是說,我們要充分利用快取。
a. 這是快取模組和其它模組不同的地方,並不是說快取中的資料越少越好,而是有用的資料越多越好。
b. 這裡有個非常好的列子,就是windows的記憶體佔用率總是非常高,很多人都表示過不滿。其實這是乙個非常好的設計。windows總是試圖盡量利用那些空閒的記憶體,用來快取磁碟上的資料,以此來提高系統的整體效能。否則你那麼大的記憶體,就為了拿來好看?
2. 如何獲取「有用」的資料。這裡,「有用」的資料的定義就是可能在不久的將來會被client用到的資料。為了得到有用的資料,我們需要預估客戶端應用的i/o 模式,比如順序讀寫,隨機讀寫等等。這裡就涉及到了「pre-fetch」演算法。
a. pre-fetch(預取演算法):是一種**客戶端應用下次讀寫的資料在**的演算法,並且把客戶要用的資料提前放入快取中,以此來提高讀的響應速度。
3. 問題來了,如果快取已經滿了,那麼如何存放新的需要快取的單元呢?這就牽涉到快取設計的另一端:淘汰演算法。
a. 相比於pre-fetch,淘汰演算法(replacement policy)更加重要。因為對於隨機的i/o, 預取演算法是無能為力的。
b. 淘汰演算法的關鍵是如何判斷乙個單元的資料比另乙個單元的資料更加重要。但需要淘汰乙個資料單元時,丟棄掉最不重要的那個資料單元,並且用它來存放新的資料。
4. 快取演算法設計的另外乙個重要的考慮因素是演算法的複雜度。或者說是實現或執行演算法帶來的額外開銷。我們希望演算法容易實現,並且額外開銷不隨著快取大小的改變而改變。包括容量的額外開銷和計算的額外開銷。
接下來的文章,我們會詳細討論預取演算法和淘汰演算法。
閒話快取 ZFS 讀快取深入研究 ARC(二)
solaris zfs arc的改動 相對於ibm arc 如我前面所說,zfs實現的arc和ibm提出的arc淘汰演算法並不是完全一致的。在某些方面,它做了一些擴充套件 zfs arc是乙個快取容量可變的快取演算法,它的容量可以根據系統可用記憶體的狀態進行調整。當系統記憶體比較充裕的時候,它的容量...
Hibernate快取 一 快取概述
hibernate快取機制對hibernate的效能發揮一直處於乙個極其重要的作用,它是持久層效能提公升的關鍵。hibernate快取介於hibernate應用和資料庫之間,快取中存放了資料庫資料的拷貝。其作用是減少訪問資料庫的頻率,從而提高應用的執行效能。hibernate在進行讀取資料的時候,根...
Hibernate快取概述
1 hibernate快取概述 快取是介於物理資料來源與應用程式之間,是資料庫資料在記憶體中的存放臨時copy的容器,其作用是為了減少應用程式對物理資料來源訪問的次數,從而提高了應用的執行效能。hibernate在進行讀取資料的時候,根據快取機制在相應的快取中查詢,如果在快取中找到了需要的資料 我們...