2011-11-05 84 views
19

我正在使用由System.Runtime.Caching.MemoryCache提供的緩存。我可以迭代.NET4 MemoryCache嗎?

我想枚舉緩存的項目,這樣我可以無效(逐出然後重新加載)項目這樣

foreach (var item in MemoryCache.Default) { item.invalidate() } 

但官方文檔found here狀態:

重要:檢索MemoryCache實例的枚舉器是一個資源密集型和阻塞操作。因此,統計員應該在生產應用中使用 。

當然,必須有一個簡單而有效的方法來迭代緩存的項目?

+0

也許你會在某種程度上需要知道什麼東西在緩存......但這意味着使用數組或其他東西。 – sinni800

+0

是的,這就是我現在正在做的事情,但這太瘋狂了,因爲這意味着我正在跟蹤緩存已經跟蹤的內容! :) –

+0

沒問題。但是如果緩存容納了大量的數據,並且你的數組只包含了抵達這些數據的信息,那麼它就能保持良好的狀態。 – sinni800

回答

9

迄今爲止所提出的建議非常好,但是我的需求仍然如下:來遍歷緩存的項目。這似乎是一個這麼簡單的任務,我希望緩存內部也有某種列表結構。文檔和MemoryCache的功能集是想要的。

因此,如上所述,我已經添加了一個列表到我的緩存適配器類,該類包含了我放置在緩存中的每個項目的引用。如果我需要迭代緩存 - 不僅是爲了失效,而是爲了收集統計數據等 - 然後我遍歷我的列表。

如果置於緩存中的項目數量沒有變化,那麼這是一個合理的解決方案。如果數字確實發生了變化,那麼您需要通過適配器類插入/刪除,以便使列表與實際緩存保持同步。雜亂,但它的工作原理,並避免在文檔中提到的性能懲罰。

希望MemoryCache緩存提供程序將在下一個平臺版本中充實。

+0

呵呵,我太慢了:)。別擔心! – sinni800

+1

我終於意識到爲什麼這堂課寫得這樣。在遍歷緩存時,您可能會遇到競爭條件,因爲在迭代期間某個項目會被驅逐!所以你需要鎖定緩存。但是,如果您有使用案例,就像我一樣,將項目設置爲永不過期,那麼這不適用(當然,由於內存不足,我的項目可能會被驅逐,但如果您的緩存是邊界案例很小,你使用的是現代服務器)。 –

+0

更多筆記。這讓我想到我的解決方案實際上非常危險*並且可能很愚蠢。接受perf命中並允許MemoryCache在迭代過程中被鎖定 - 或者使用其他方式使其所有項目無效,這是明智得多的。如果高速緩存不是經常失效的話,那麼可以接受perf的命中就好了:只需要考慮加熱高速緩存所花費的時間 - 使整個事情失效也不例外。儘管如此,文檔還是警告不要在生產代碼中使用枚舉器:我想知道爲什麼?也許還有其他問題我不知道? –

-2

在2014年,

這是讓所有的物品的正確方法:

Dim AllItems = MemoryCache.Default.Select(Of ItemType)(Function(O) O.Value)

希望這可以幫助別人。

+2

Downvote。這與「枚舉」緩存項相同,正如OP在官方文檔中指出的那樣,緩存項是'資源密集型',應該避免。請參閱[枚舉問題](http://stackoverflow.com/a/22388943/219516)。 – publicgk

+0

對不起@publicgk我沒有完全讀完這個問題。 – Dejisys

相關問題