asp.net頁面清除緩存2(轉)

ASP.NET 提供三種主要形式的緩存:頁面級輸出緩存、用戶控件級輸出緩存(或稱爲片斷緩存)和緩存 API。html

輸出緩存和片斷緩存的優勢是很是易於實現,在大多數狀況下,使用這兩種緩存就足夠了。而緩存 API 則提供了額外的靈活性(其實是至關大的靈活性),可用於在應用程序的每一層利用緩存。web

 

Steve 的緩存提示

 

儘早緩存;常常緩存數據庫

您應該在應用程序的每一層都實現緩存。向數據層、業務邏輯層、UI 或輸出層添加緩存支持。內存如今很是便宜 — 所以,經過以智能的方式在整個應用程序中實現緩存,能夠得到很大的性能提升。數組

 

緩存能夠掩蓋許多過失瀏覽器

緩存是一種無需大量時間和分析就能夠得到「足夠良好的」性能的方法。這裏再次強調,內存如今很是便宜,所以,若是您能經過將輸出緩存 30 秒,而不是花上一成天甚至一週的時間嘗試優化代碼或數據庫就能夠得到所需的性能,您確定會選擇緩存解決方案(假設能夠接受 30 秒的舊數據)。緩存正是那些利用 20% 付出得到 80% 回報的特性之一,所以,要提升性能,應該首先想到緩存。不過,若是設計很糟糕,最終卻有可能帶來不良的後果,所以,您固然也應該儘可能正確地設計應用程序。但若是您只是須要當即得到足夠高的性能,緩存就是您的最佳選擇,您能夠在之後有時間的時候再儘快從新設計應用程序。緩存

 

1 頁面級輸出緩存

做爲最簡單的緩存形式,輸出緩存只是在內存中保留爲響應請求而發送的 HTML 的副本。其後再有請求時將提供緩存的輸出,直到緩存到期,這樣,性能有可能獲得很大的提升(取決於須要多少開銷來建立原始頁面輸出 - 發送緩存的輸出老是很快,而且比較穩定)。服務器

 

實現asp.net

要實現頁面輸出緩存,只要將一條 OutputCache 指令添加到頁面便可。函數

<%@ OutputCache Duration="60" VaryByParam="*" %>

如同其餘頁面指令同樣,該指令應該出如今 ASPX 頁面的頂部,即在任何輸出以前。它支持五個屬性(或參數),其中兩個是必需的。佈局

 

 

 

Duration

必需屬性。頁面應該被緩存的時間,以秒爲單位。必須是正整數。

Location

指定應該對輸出進行緩存的位置。若是要指定該參數,則必須是下列選項之一:Any、Client、Downstream、None、Server 或 ServerAndClient。

VaryByParam

必需屬性。Request 中變量的名稱,這些變量名應該產生單獨的緩存條目。"none" 表示沒有變更。"*" 可用於爲每一個不一樣的變量數組建立新的緩存條目。變量之間用 ";" 進行分隔。

VaryByHeader

基於指定的標頭中的變更改變緩存條目。

VaryByCustom

容許在 global.asax 中指定自定義變更(例如,"Browser")。

 

 

利用必需的 Duration 和 VaryByParam 選項的組合能夠處理大多數狀況。

例如,若是您的產品目錄容許用戶基於 categoryID 和頁變量查看目錄頁,您能夠用參數值爲 "categoryID;page" 的 VaryByParam 將產品目錄緩存一段時間(若是產品不是隨時都在改變,一小時仍是能夠接受的,所以,持續時間是 3600 秒)。這將爲每一個種類的每一個目錄頁建立單獨的緩存條目。每一個條目從其第一個請求算起將維持一個小時。

 

VaryByHeader 和 VaryByCustom 主要用於根據訪問頁面的客戶端對頁面的外觀或內容進行自定義。同一個 URL 可能須要同時爲瀏覽器和移動電話客戶端呈現輸出,所以,須要針對不一樣的客戶端緩存不一樣的內容版本。或者,頁面有可能已經針對 IE 進行了優化,但須要能針對 Netscape 或 Opera 徹底下降優化(而不只僅是破壞頁面)。後一個例子很是廣泛,咱們將提供一個說明如何實現此目標的示例:

 

示例: VaryByCustom 用於支持瀏覽器自定義

爲了使每一個瀏覽器都具備單獨的緩存條目,VaryByCustom 的值能夠設置爲 "browser"。此功能已經內置在緩存模塊中,而且將針對每一個瀏覽器名稱和主要版本插入單獨的頁面緩存版本。

<%@ OutputCache Duration="60" VaryByParam="None" VaryByCustom="browser" %>
使用緩存配置文件以聲明方式設置頁的可緩存性
1在應用程序的 Web.config 文件中定義緩存配置文件在配置文件中包括 duration 和 varyByParam 設. 
下面的 <caching> 配置元素定義名爲 Cache30Seconds的緩存配置文件,它將在服務器上將頁緩存30秒。
<system.web>
<caching>
 <outputCacheSettings>
    <outputCacheProfiles>
      <add name="Cache30Seconds" duration="30" varyByParam="none" />
    </outputCacheProfiles>
 </outputCacheSettings>
</caching>
</system.web>
2在使用配置文件的每一個 ASP.NET 頁中包含 @ OutputCache 指令,並將 CacheProfile 屬性設置爲 Web.config 文件中定義的緩存配置文件的名稱。 
下面的代碼指定頁應當使用名爲 Cache30Seconds的緩存配置文件:
  
<%@ OutputCache CacheProfile="Cache30Seconds" %>

2 片斷緩存,用戶控件輸出緩存


 
緩存整個頁面一般並不可行,由於頁面的某些部分是針對用戶定製的。不過,頁面的其餘部分是整個應用程序共有的。這些部分最適合使用片斷緩存和用戶控件進行緩存。菜單和其餘佈局元素,尤爲是那些從數據源動態生成的元素,也應該用這種方法進行緩存。若是須要,能夠將緩存的控件配置爲基於對其控件(或其餘屬性)的更改或由頁面級輸出緩存支持的任何其餘變更進行改變。使用同一組控件的幾百個頁面還能夠共享那些控件的緩存條目,而不是爲每一個頁面保留單獨的緩存版本。
 
實現 
片斷緩存使用的語法與頁面級輸出緩存同樣,但其應用於用戶控件(.ascx 文件)而不是 Web 窗體(.aspx 文件)。除了 Location 屬性,對於 OutputCache 在 Web 窗體上支持的全部屬性,用戶控件也一樣支持。用戶控件還支持名爲 VaryByControl 的 OutputCache 屬性,該屬性將根據用戶控件(一般是頁面上的控件,例如,DropDownList)的成員的值改變該控件的緩存。若是指定了 VaryByControl,能夠省略 VaryByParam。最後,在默認狀況下,對每一個頁面上的每一個用戶控件都單獨進行緩存。不過,若是一個用戶控件不隨應用程序中的頁面改變,而且在全部頁面都使用相同的名稱,則能夠應用 Shared="true" 參數,該參數將使用戶控件的緩存版本供全部引用該控件的頁面使用。
 
示例
<%@ OutputCache Duration="60" VaryByParam="*" %>

該示例將緩存用戶控件 60 秒,而且將針對查詢字符串的每一個變更、針對此控件所在的每一個頁面建立單獨的緩存條目。
<%@ OutputCache Duration="60" VaryByParam="none" VaryByControl="CategoryDropDownList" %>

該示例將緩存用戶控件 60 秒,而且將針對 CategoryDropDownList 控件的每一個不一樣的值、針對此控件所在的每一個頁面建立單獨的緩存條目。
<%@ OutputCache Duration="60" VaryByParam="none" VaryByCustom="browser" Shared="true %>

最後,該示例將緩存用戶控件 60 秒,而且將針對每一個瀏覽器名稱和主要版本建立一個緩存條目。而後,每一個瀏覽器的緩存條目將由引用此用戶控件的全部頁面共享(只要全部頁面都用相同的 ID 引用該控件便可)。
 

3緩存 API,使用 Cache 對象


頁面級和用戶控件級輸出緩存的確是一種能夠迅速而簡便地提升站點性能的方法,可是在 ASP.NET 中,緩存的真正靈活性和強大功能是經過 Cache 對象提供的。使用 Cache 對象,您能夠存儲任何可序列化的數據對象,基於一個或多個依賴項的組合來控制緩存條目到期的方式。這些依賴項能夠包括自從項被緩存後通過的時間、自從項上次被訪問後通過的時間、對文件和/或文件夾的更改以及對其餘緩存項的更改,在略做處理後還能夠包括對數據庫中特定表的更改。
 Cache 中存儲數據 
在 Cache 中存儲數據的最簡單的方法就是使用一個鍵爲其賦值,就像 HashTable 或 Dictionary 對象同樣:
Cache["key"] = "value";
這種作法將在緩存中存儲項,同時不帶任何依賴項,所以它不會到期,除非緩存引擎爲了給其餘緩存數據提供空間而將其刪除。要包括特定的緩存依賴項,可以使用 Add() 或 Insert() 方法。其中每一個方法都有幾個重載。Add() 和 Insert() 之間的惟一區別是,Add() 返回對已緩存對象的引用,而 Insert() 沒有返回值(在 C# 中爲空,在 VB 中爲 Sub)。
 
示例
Cache.Insert("key", myXMLFileData, new System.Web.Caching.CacheDependency(Server.MapPath("users.xml")));

該示例可將文件中的 xml 數據插入緩存,無需在之後請求時從文件讀取。 CacheDependency 的做用是確保緩存在文件更改後當即到期,以即可以從文件中提取最新數據,從新進行緩存。若是緩存的數據來自若干個文件,還能夠指定一個文件名的數組。
Cache.Insert("dependentkey", myDependentData, new System.Web.Caching.CacheDependency(new string[] {}, new string[] {"key"}));

該示例可插入鍵值爲 "key" 的第二個數據塊(取決因而否存在第一個數據塊)。若是緩存中不存在名爲 "key" 的鍵,或者若是與該鍵相關聯的項已到期或被更新,則 "dependentkey" 的緩存條目將到期。
Cache.Insert("key", myTimeSensitiveData, null, DateTime.Now.AddMinutes(1), TimeSpan.Zero);

絕對到期:此示例將對受時間影響的數據緩存一分鐘,一分鐘事後,緩存將到期。注意,絕對到期和滑動到期(見下文)不能一塊兒使用。
Cache.Insert("key", myFrequentlyAccessedData, null, System.Web.Caching.Cache.NoAbsoluteExpiration, TimeSpan.FromMinutes(1));

滑動到期:此示例將緩存一些頻繁使用的數據。數據將在緩存中一直保留下去,除非數據未被引用的時間達到了一分鐘。注意,滑動到期和絕對到期不能一塊兒使用。
 
更多選項 
除了上面提到的依賴項,咱們還能夠指定項的優先級(依次爲 low、high、NotRemovable,它們是在 System.Web.Caching.CacheItemPriority 枚舉中定義的)以及當緩存中的項到期時調用的CacheItemRemovedCallback 函數。大多數時候,默認的優先級已經足夠了 — 緩存引擎能夠正常完成任務並處理緩存的內存管理。CacheItemRemovedCallback 選項考慮到一些頗有趣的可能性,但實際上它不多使用。不過,爲了說明該方法,我將提供它的一個使用示例:
CacheItemRemovedCallback 示例
System.Web.Caching.CacheItemRemovedCallback callback = new System.Web.Caching.CacheItemRemovedCallback (OnRemove); Cache.Insert("key",myFile,null, System.Web.Caching.Cache.NoAbsoluteExpiration, TimeSpan.Zero, System.Web.Caching.CacheItemPriority.Default, callback); . . . public static void OnRemove(string key, object cacheItem, System.Web.Caching.CacheItemRemovedReason reason) { AppendLog("The cached value with key '" + key + "' was removed from the cache. Reason: " + reason.ToString()); }

該示例將使用
AppendLog()

方法(這裏不討論該方法,請參閱 Writing Entries to Event Logs)中定義的任何邏輯來記錄緩存中的數據到期的緣由。經過在從緩存中刪除項時記錄這些項並記錄刪除的緣由,您能夠肯定是否在有效地使用緩存或者您是否可能須要增長服務器上的內存。注意,callback 是一個靜態(在 VB 中爲 Shared)方法,建議使用該方法的緣由是,若是不使用它,保存回調函數的類的實例將保留在內存中,以支持回調(對 static/Shared 方法則沒有必要)。 
該特性有一個潛在的用處 — 在後臺刷新緩存的數據,這樣用戶永遠都沒必要等待數據被填充,但數據始終保持相對較新的狀態。但實際上,此特性並不適用於當前版本的緩存 API,由於在從緩存中刪除緩存的項以前,不觸發或不完成回調。所以,用戶將頻繁地發出嘗試訪問緩存值的請求,而後發現緩存值爲空,不得不等待緩存值的從新填充。我但願在將來的 ASP.NET 版本中看到一個附加的回調,能夠稱爲 CachedItemExpiredButNotRemovedCallback,若是定義了該回調,則必須在刪除緩存項以前完成執行。
 
緩存數據引用模式 
每當咱們嘗試訪問緩存中的數據時,都應該考慮到一種狀況,那就是數據可能已經不在緩存中了。所以,下面的模式應該廣泛適用於您對緩存的數據的訪問。在這種狀況下,咱們假定已緩存的數據是一個數據表。
public DataTable GetCustomers(bool BypassCache) { string cacheKey = "CustomersDataTable"; object cacheItem = Cache[cacheKey] as DataTable; if((BypassCache) || (cacheItem == null)) { cacheItem = GetCustomersFromDataSource(); Cache.Insert(cacheKey, cacheItem, null, DateTime.Now.AddSeconds(GetCacheSecondsFromConfig(cacheKey), TimeSpan.Zero); } return (DataTable)cacheItem; }

關於此模式,有如下幾點須要注意:
  • 某些值(例如,cacheKey、cacheItem 和緩存持續時間)是一次定義的,而且只定義一次。

  • 能夠根據須要跳過緩存 — 例如,當註冊一個新客戶並重定向到客戶列表後,最好的作法可能就是跳過緩存,用最新數據從新填充緩存,該數據包括新插入的客戶。

  • 緩存只能訪問一次。這種作法能夠提升性能,並確保不會發生 NullReferenceExceptions,由於該項在第一次被檢查時是存在的,但第二次檢查以前就已經到期了。

  • 該模式使用強類型檢查。C# 中的 "as" 運算符嘗試將對象轉換爲類型,若是失敗或該對象爲空,則只返回 null(空)。

  • 持續時間存儲在配置文件中。在理想的狀況下,全部的緩存依賴項(不管是基於文件的,或是基於時間的,仍是其餘類型的依賴項)都應該存儲在配置文件中,這樣就能夠進行更改並輕鬆地測量性能。我還建議您指定默認緩存持續時間,並且,若是沒有爲所使用的 cacheKey 指定持續時間,就讓 GetCacheSecondsFromConfig() 方法使用該默認持續時間。


 
小結
緩存可使應用程序的性能獲得很大的提升,所以在設計應用程序以及對應用程序進行性能測試時應該予以考慮。應用程序總會或多或少地受益於緩存,固然有些應用程序比其餘應用程序更適合使用緩存。對 ASP.NET 提供的緩存選項的深入理解是任何 ASP.NET 開發人員應該掌握的重要技巧。

 

 

轉載至:http://blog.sina.com.cn/s/blog_67aaf4440100q4aw.html

相關文章
相關標籤/搜索