主頁(yè) > 知識(shí)庫(kù) > 全面剖析.Net環(huán)境下的緩存技術(shù)

全面剖析.Net環(huán)境下的緩存技術(shù)

熱門(mén)標(biāo)簽:地圖標(biāo)注的公司有哪些 地圖定位圖標(biāo)標(biāo)注 地圖標(biāo)注專業(yè)團(tuán)隊(duì) 濮陽(yáng)外呼電銷系統(tǒng)怎么樣 400電話辦理哪家性價(jià)比高 代理接電話機(jī)器人如何取消 遂寧市地圖標(biāo)注app 塔城代理外呼系統(tǒng) 天心智能電銷機(jī)器人

一、 概念
1.1   緩存能解決的問(wèn)題
· 性能——將相應(yīng)數(shù)據(jù)存儲(chǔ)起來(lái)以避免數(shù)據(jù)的重復(fù)創(chuàng)建、處理和傳輸,可有效提高性能。比如將不改變的數(shù)據(jù)緩存起來(lái),例如國(guó)家列表等,這樣能明顯提高web程序的反應(yīng)速度;

· 穩(wěn)定性——同一個(gè)應(yīng)用中,對(duì)同一數(shù)據(jù)、邏輯功能和用戶界面的多次請(qǐng)求時(shí)經(jīng)常發(fā)生的。當(dāng)用戶基數(shù)很大時(shí),如果每次請(qǐng)求都進(jìn)行處理,消耗的資源是很大的浪費(fèi),也同時(shí)造成系統(tǒng)的不穩(wěn)定。例如,web應(yīng)用中,對(duì)一些靜態(tài)頁(yè)面的呈現(xiàn)內(nèi)容進(jìn)行緩存能有效的節(jié)省資源,提高穩(wěn)定性。而緩存數(shù)據(jù)也能降低對(duì)數(shù)據(jù)庫(kù)的訪問(wèn)次數(shù),降低數(shù)據(jù)庫(kù)的負(fù)擔(dān)和提高數(shù)據(jù)庫(kù)的服務(wù)能力;

· 可用性——有時(shí),提供數(shù)據(jù)信息的服務(wù)可能會(huì)意外停止,如果使用了緩存技術(shù),可以在一定時(shí)間內(nèi)仍正常提供對(duì)最終用戶的支持,提高了系統(tǒng)的可用性。

1.2   理解狀態(tài)
在深入介紹緩存技術(shù)之前,需要對(duì)狀態(tài)有一個(gè)認(rèn)識(shí),因?yàn)榫彺婵梢哉f(shuō)是狀態(tài)管理的框架。理解狀態(tài)的含義和它的一些特性——比如生存期和生存范圍——對(duì)決定是否緩存和選擇合適的緩存技術(shù)有很大幫助。狀態(tài)是指一些數(shù)據(jù),在應(yīng)用系統(tǒng)某個(gè)時(shí)間點(diǎn)上,數(shù)據(jù)的狀態(tài)和條件。這些數(shù)據(jù)可能是永久性的存儲(chǔ)在數(shù)據(jù)庫(kù)中,可能是只在內(nèi)存里停留一會(huì),也可能是按照某個(gè)邏輯存活(比如多長(zhǎng)時(shí)間后釋放),它的應(yīng)用范圍可能是所有用戶可訪問(wèn),可能是單個(gè)用戶有權(quán)限;

1.2.1  狀態(tài)的生存期
生存期是指數(shù)據(jù)保持有效性的時(shí)間區(qū)間,也就是從創(chuàng)建到移除的時(shí)間間隔。通常的生存期有以下幾種:

·永久狀態(tài)Permanent State——應(yīng)用程序使用的永久數(shù)據(jù);

·進(jìn)程狀態(tài)Process State——只在進(jìn)程周期內(nèi)有效;

·會(huì)話狀態(tài)Session State——和特定的用戶會(huì)話有關(guān);

·消息狀態(tài)Message State——處理某個(gè)消息的時(shí)間內(nèi)有效;

1.2.2  狀態(tài)的范圍
狀態(tài)的范圍指對(duì)該狀態(tài)有訪問(wèn)權(quán)限的物理或邏輯范圍。

·物理范圍指可以被訪問(wèn)到的狀態(tài)數(shù)據(jù)存放的物理位置,通常包括:

1、  組織Organization——在一個(gè)組織內(nèi)的所有應(yīng)用程序可以訪問(wèn)狀態(tài)數(shù)據(jù);

2、  場(chǎng)Farm——在應(yīng)用場(chǎng)范圍內(nèi)的任何機(jī)器上都可以訪問(wèn);

3、  機(jī)器Machine——單個(gè)機(jī)器范圍內(nèi)可以訪問(wèn);

4、  進(jìn)程Process——進(jìn)程內(nèi)的訪問(wèn)許可;

5、  應(yīng)用域AppDomain——應(yīng)用程序域內(nèi)的訪問(wèn)許可。

·邏輯范圍指可訪問(wèn)狀態(tài)數(shù)據(jù)的邏輯范圍,常見(jiàn)的有:

1、  應(yīng)用程序Application;

2、  業(yè)務(wù)流程Business Process;

3、  角色Role;

4、  用戶User;

1.2.3  狀態(tài)數(shù)據(jù)的陳舊
緩存的狀態(tài)數(shù)據(jù)只是主數(shù)據(jù)(Master State Data)的快照,由于數(shù)據(jù)源可能被修改,所以狀態(tài)數(shù)據(jù)就有會(huì)陳舊的特性。合理利用此特性和將數(shù)據(jù)陳舊的負(fù)面影響最小化是緩存狀態(tài)數(shù)據(jù)的一個(gè)重要任務(wù)。你可以以一下方式定義數(shù)據(jù)的陳舊依據(jù):

·主數(shù)據(jù)更改的可能性——隨著時(shí)間的推進(jìn),主數(shù)據(jù)更改的可能是否大大增加?安照這一點(diǎn)來(lái)決定緩存狀態(tài)數(shù)據(jù)的陳舊;

·更改的相關(guān)性——主數(shù)據(jù)更新時(shí),緩存的狀態(tài)數(shù)據(jù)不相應(yīng)更新是不是造成影響系統(tǒng)的使用?比如,更改系統(tǒng)的外觀風(fēng)格并不會(huì)對(duì)業(yè)務(wù)造成很大影響。

1.2.4  狀態(tài)數(shù)據(jù)陳舊的容忍度
緩存狀態(tài)數(shù)據(jù)的陳舊對(duì)業(yè)務(wù)流程的影響稱為容忍度,應(yīng)用系統(tǒng)的可以為不能容忍(No Tolerance)和一定程度的容忍(some Tolerance),前者必須和主數(shù)據(jù)同步更新,后者允許一定時(shí)間或一定范圍的陳舊,判斷標(biāo)準(zhǔn)就是對(duì)業(yè)務(wù)流程的影響度。

1.2.5  理解狀態(tài)數(shù)據(jù)的轉(zhuǎn)換過(guò)程
狀態(tài)的另一個(gè)屬性是在不同階段的表現(xiàn)形式。在數(shù)據(jù)庫(kù)中存儲(chǔ)的是原始格式的數(shù)據(jù),業(yè)務(wù)流程中的是處理過(guò)的數(shù)據(jù),給最終用戶呈現(xiàn)的則是另外的形式。如下表所示:

當(dāng)決定緩存數(shù)據(jù)時(shí),應(yīng)該考慮緩存哪個(gè)階段(哪種形式)的狀態(tài)數(shù)據(jù)。以下方針有助于你做決定:

· 當(dāng)業(yè)務(wù)邏輯可以容忍緩存數(shù)據(jù)的陳舊時(shí)就緩存原始數(shù)據(jù);原始數(shù)據(jù)可以緩存在數(shù)據(jù)庫(kù)訪問(wèn)組件和服務(wù)代理中;

·緩存處理過(guò)的數(shù)據(jù)以減少處理時(shí)間和資源;處理過(guò)的數(shù)據(jù)可以緩存在業(yè)務(wù)邏輯組件和服務(wù)接口中。

·當(dāng)需要呈現(xiàn)的數(shù)據(jù)量很大并且控件的呈現(xiàn)時(shí)間很長(zhǎng)時(shí),緩存呈現(xiàn)數(shù)據(jù)(比如包含大數(shù)據(jù)量的Treeview控件)。這種數(shù)據(jù)應(yīng)該被緩存在UI控件中。

1.3   為什么要緩存數(shù)據(jù)
在應(yīng)用程序中緩存數(shù)據(jù)有以下好處:

·減少交互的通訊量——緩存數(shù)據(jù)能有效減少在進(jìn)程和機(jī)器間的傳輸量;

·降低系統(tǒng)中的處理量——減少處理次數(shù);

·降低需要做的磁盤(pán)訪問(wèn)次數(shù)——比如緩存在內(nèi)存中的數(shù)據(jù)。

1.4   數(shù)據(jù)應(yīng)該被緩存在哪里
緩存數(shù)據(jù)只是一份主數(shù)據(jù)的拷貝,它可能在內(nèi)存中或以不同的表現(xiàn)形式保存在硬盤(pán)上,也就是說(shuō),離說(shuō)句的使用者越近越好。所以,除了考慮要緩存哪些數(shù)據(jù)以外,數(shù)據(jù)緩存在哪里也是一個(gè)主要的考量點(diǎn)。這個(gè)問(wèn)題分為以下兩個(gè)范圍:

1、  存儲(chǔ)類型Storage Type——數(shù)據(jù)可用的物理存儲(chǔ)位置;

2、  層間的架構(gòu)元素(Layered architecture elements)——數(shù)據(jù)可用的邏輯存儲(chǔ)位置。

1.4.1  存儲(chǔ)類型
緩存有很多實(shí)現(xiàn)方法,所有這些可以被分為兩類,基于內(nèi)存的緩存和基于磁盤(pán)的緩存:

1、  內(nèi)存駐留緩存——包含在內(nèi)存中臨時(shí)存儲(chǔ)數(shù)據(jù)的所有實(shí)現(xiàn)方法,通常在以下情況下使用:

a)       應(yīng)用程序頻繁使用同樣的數(shù)據(jù);

b)       應(yīng)用程序需要經(jīng)常獲取數(shù)據(jù);

通過(guò)將數(shù)據(jù)保留在內(nèi)存中,你可以有效降低昂貴的磁盤(pán)訪問(wèn)操作,也可以通過(guò)將數(shù)據(jù)保留在使用者進(jìn)程中來(lái)最大程度的減少跨進(jìn)程的數(shù)據(jù)傳輸。

2、  磁盤(pán)駐留緩存——這種技術(shù)包含所有使用磁盤(pán)作為存儲(chǔ)介質(zhì)的緩存技術(shù),如文件和數(shù)據(jù)庫(kù)。在以下情況下基于磁盤(pán)的緩存是很有效的:

a)       處理大數(shù)據(jù)量時(shí);

b)       應(yīng)用服務(wù)提供的數(shù)據(jù)可能并不是總能使用(比如離線的情況);

c)       緩存的數(shù)據(jù)必須能在進(jìn)程回收和機(jī)器重啟的情況下保持有效;

通過(guò)緩存處理過(guò)的數(shù)據(jù),你可以有效降低數(shù)據(jù)處理的負(fù)擔(dān),同時(shí)可減少數(shù)據(jù)交互的代價(jià)。

1.4.2  架構(gòu)間元素
應(yīng)用程序中的每個(gè)邏輯層的組件都會(huì)處理數(shù)據(jù),當(dāng)使用這些組件進(jìn)行工作時(shí),你需要考慮哪些數(shù)據(jù)可以被緩存起來(lái),還有以哪種方式進(jìn)行緩存會(huì)對(duì)程序的整體性能和可用性有幫助,以上的這些元素都可以緩存相應(yīng)的數(shù)據(jù)。當(dāng)然,要考慮的遠(yuǎn)不止這些。

1.5   實(shí)施緩存時(shí)的考慮
當(dāng)設(shè)計(jì)一個(gè)緩存方案時(shí),不但要考慮緩存哪些數(shù)據(jù)、數(shù)據(jù)緩存到哪里,還有其它的因素需要考慮。

1.5.1  格式和訪問(wèn)模式
當(dāng)決定是否緩存一個(gè)對(duì)象時(shí),關(guān)于數(shù)據(jù)的格式和訪問(wèn)機(jī)制,你需要考慮三個(gè)主要問(wèn)題:

1、  線程安全——當(dāng)緩存的內(nèi)容可以被多個(gè)線程訪問(wèn)時(shí),使用某種鎖定機(jī)制來(lái)保證數(shù)據(jù)不會(huì)被兩個(gè)線程同時(shí)操作;

2、  序列化——將一個(gè)對(duì)象緩存時(shí),需要將它序列化以便保存,所以包緩存的對(duì)象必須支持序列化;

3、  規(guī)格化緩存數(shù)據(jù)——緩存數(shù)據(jù)時(shí),相對(duì)于要使用的數(shù)據(jù)格式而言,要保證數(shù)據(jù)的格式是優(yōu)化過(guò)的。

1.5.2  內(nèi)容加載
在使用緩存數(shù)據(jù)前,必須將數(shù)據(jù)加載到緩存中,有兩種機(jī)制來(lái)加載數(shù)據(jù):

·提前加載Proactive Load——使用這種方式時(shí),你提前將所有的狀態(tài)數(shù)據(jù)加載到緩存中,可能在應(yīng)用程序或線程啟動(dòng)時(shí)進(jìn)行,然后在應(yīng)用程序或線程的生存期內(nèi)一直緩存;

·動(dòng)態(tài)加載Reactive Load——或稱反應(yīng)式加載,當(dāng)使用這種方法時(shí),在應(yīng)用程序請(qǐng)求數(shù)據(jù)時(shí)取到數(shù)據(jù),并且將它緩存起來(lái)以備后續(xù)使用。

1.5.3  過(guò)期策略
另外一個(gè)關(guān)鍵因素是如何保持緩存數(shù)據(jù)和主數(shù)據(jù)(文件或數(shù)據(jù)庫(kù)或其他的應(yīng)用程序資源)的一致性,你可以定義過(guò)期策略來(lái)決定緩存中的內(nèi)容,如已經(jīng)緩存的時(shí)間或者收到其他資源的通知。

1.5.4  安全性
當(dāng)緩存數(shù)據(jù)時(shí),需要非常清楚緩存中數(shù)據(jù)的潛在安全威脅。緩存中的數(shù)據(jù)可能會(huì)被別的進(jìn)程訪問(wèn)或修改,而此進(jìn)程對(duì)主數(shù)據(jù)是沒(méi)有權(quán)限的。原因是當(dāng)數(shù)據(jù)存儲(chǔ)在原始位置時(shí),有相應(yīng)的安全機(jī)制來(lái)保護(hù)它,當(dāng)數(shù)據(jù)被帶出傳統(tǒng)的安全邊界時(shí),需要有同等的安全機(jī)制。

1.5.5  管理
當(dāng)你緩存數(shù)據(jù)時(shí),應(yīng)用系統(tǒng)需要的維護(hù)工作加大了。在發(fā)布應(yīng)用程序時(shí),需要配置相應(yīng)的屬性,比如緩存的大小限制和清除策略。同時(shí)要使用某種機(jī)制來(lái)監(jiān)控緩存的效率(比如事件日志和性能計(jì)數(shù)器)

1.6   小結(jié)
第一節(jié)內(nèi)容簡(jiǎn)單介紹了緩存技術(shù)中的概念、緩存數(shù)據(jù)的原因和方案、優(yōu)勢(shì)、實(shí)施緩存方案時(shí)的考慮等基本內(nèi)容?,F(xiàn)在你對(duì)緩存中涉及的內(nèi)容有了一個(gè)大致了解,下面著重介紹可用的緩存技術(shù)。

二、緩存技術(shù)
本節(jié)將介紹以下技術(shù):

使用Asp.Net緩存;

使用Remoting Singleton緩存;

使用內(nèi)存映射文件;

使用SQL Server緩存;

使用靜態(tài)變量緩存;

使用Asp.net 會(huì)話狀態(tài)(Session State);

使用Asp.net客戶端緩存和狀態(tài);

使用Internet Explorer緩存。

2.1 Asp.net緩存
將常用的數(shù)據(jù)保存在內(nèi)存中對(duì)asp的開(kāi)發(fā)人員來(lái)說(shuō)并不陌生,Session對(duì)象和Application對(duì)象提供鍵值對(duì)來(lái)緩存數(shù)據(jù),Session對(duì)象保存和單個(gè)用戶有關(guān)的數(shù)據(jù),Application對(duì)象可保留和應(yīng)用程序有關(guān)的數(shù)據(jù),每個(gè)用戶都可以訪問(wèn)。

在Asp.net中,提供了專門(mén)用于緩存數(shù)據(jù)的Cache對(duì)象,它的應(yīng)用范圍是應(yīng)用程序域。生存期是和應(yīng)用程序緊密相關(guān)的,每當(dāng)應(yīng)用程序啟動(dòng)的時(shí)候就重新創(chuàng)建Cache對(duì)象。它域Application對(duì)象的主要區(qū)別就是提供了專門(mén)用于緩存管理的特性,比如依賴和過(guò)期策略。

你可以使用Cache對(duì)象和它的屬性來(lái)實(shí)現(xiàn)高級(jí)的緩存功能,同時(shí)可以利用Asp.net Cache來(lái)對(duì)客戶端輸出的響應(yīng)內(nèi)容進(jìn)行緩存。關(guān)于Asp.net中的緩存技術(shù),有以下內(nèi)容要介紹:

2.1.1  編程緩存Programmatic Caching
Cache對(duì)象定義在System.Web.Caching命名空間,可以使用HttpContext類的Cache屬性或Page對(duì)象的Cache屬性來(lái)得到Cache的引用,Cache對(duì)象除了存儲(chǔ)鍵值對(duì)以外,還可以存儲(chǔ).net框架的對(duì)象。下面介紹相應(yīng)的依賴和過(guò)期策略。

2.1.1.1 依賴和過(guò)期策略
當(dāng)向緩存中加數(shù)據(jù)時(shí),可以指定它的依賴關(guān)系來(lái)實(shí)現(xiàn)在某些情況下強(qiáng)制移除它??捎玫姆桨赴ㄒ韵聨追N:

·文件依賴(File Dependency)——當(dāng)硬盤(pán)上的某個(gè)(某些)文件更改時(shí),強(qiáng)制移除緩存數(shù)據(jù);如:

CacheDependency cDependency = new

CacheDependency(Server.MapPath("authors.xml"));

Cache.Insert("CachedItem", item, cDependency);

·鍵值依賴(Key Dependency)——指定緩存中的某個(gè)數(shù)據(jù)項(xiàng)更改時(shí)移除。如:

// Create a cache entry.

Cache["key1"] = "Value 1";

// Make key2 dependent on key1.

String[] dependencyKey = new String[1];

dependencyKey[0] = "key1";

CacheDependency dependency = new CacheDependency(null, dependencyKey);

Cache.Insert("key2", "Value 2", dependency);

·基于時(shí)間的過(guò)期策略——按照預(yù)先定義的時(shí)間策略來(lái)使數(shù)據(jù)失效,可以是絕對(duì)時(shí)間(如某個(gè)日期的18:00)也可以是相對(duì)現(xiàn)在的相對(duì)時(shí)間。如:

/// Absolute expiration

Cache.Insert("CachedItem", item, null, DateTime.Now.AddSeconds(5),Cache.NoSlidingExpiration);

/// Sliding expiration

Cache.Insert("CachedItem", item, null, Cache.NoAbsoluteExpiration,

TimeSpan.FromSeconds(5));

使用太短和太長(zhǎng)的過(guò)期時(shí)間都不行,不是造成用不上的緩存數(shù)據(jù),就是緩存了陳舊的數(shù)據(jù)并加重了緩存負(fù)擔(dān),所以可以使用高并發(fā)的測(cè)試來(lái)決定過(guò)期時(shí)間的最佳值。

·另外有個(gè)問(wèn)題就是如何實(shí)現(xiàn)對(duì)數(shù)據(jù)庫(kù)的依賴,這就要求實(shí)現(xiàn)自己的通知機(jī)制,當(dāng)數(shù)據(jù)庫(kù)數(shù)據(jù)改變時(shí)能夠通知你的緩存數(shù)據(jù)改變。

由于數(shù)據(jù)會(huì)過(guò)期,所以當(dāng)使用緩存中的數(shù)據(jù)時(shí),必須檢查數(shù)據(jù)的有效性。如以下代碼:

string data = (string)Cache["MyItem"];

if (data == null)

{

data = GetData();

Cache.Insert("MyItem", data);

}

DoSomeThingWithData(data);

依賴和過(guò)期策略指定了緩存中數(shù)據(jù)的移除方式,有時(shí)候你可能需要在移除發(fā)生時(shí)做一些工作,這能靠寫(xiě)代碼來(lái)實(shí)現(xiàn)這一點(diǎn),這就是我們要講到的。

2.1.1.2 使用緩存回調(diào)(Cache Callback)
你可以定義回調(diào),這樣當(dāng)移除自動(dòng)發(fā)生時(shí), 你可以不移除它或者使用新的數(shù)據(jù)來(lái)替換它。如:

CacheItemRemovedCallback onRemove = new CacheItemRemovedCallback(this.RemovedCallback);

Cache.Insert("CachedItem",

item,

null,

Cache.NoAbsoluteExpiration,

Cache.NoSlidingExpiration,

CacheItemPriority.Default,

onRemove);

// Implement the function to handle the expiration of the cache.

public void RemovedCallback(string key, object value, CacheItemRemovedReason r)

{

// Test whether the item is expired, and reinsert it into the cache.

if (r == CacheItemRemovedReason.Expired)

{

// Reinsert it into the cache again.

CacheItemRemovedCallback onRemove = null;

onRemove = new CacheItemRemovedCallback(this.RemovedCallback);

Cache.Insert(key,

value,

null,

Cache.NoAbsoluteExpiration,

Cache.NoSlidingExpiration,

CacheItemPriority.Default,

onRemove);

}

}

2.1.1.3 對(duì)緩存項(xiàng)使用優(yōu)先級(jí)
當(dāng)運(yùn)行應(yīng)用程序的服務(wù)器內(nèi)存不足時(shí),會(huì)自動(dòng)清除緩存中的數(shù)據(jù),稱為“清除scavenging”。此時(shí),Cache對(duì)象根據(jù)緩存項(xiàng)的優(yōu)先級(jí)來(lái)決定先移除哪些緩存數(shù)據(jù),你可以在代碼中指定緩存項(xiàng)的優(yōu)先級(jí)。參看MSDN中“CacheItemPriority 枚舉”,如:

Cache.Insert("DSN", connectionString, null, d, t, CacheItemPriority.High, onRemove);

2.1.1.4 刷新數(shù)據(jù)(清除緩存)
沒(méi)有直接的方法來(lái)刷新Asp.net的輸出緩存,但是有替代方法(設(shè)置所有數(shù)據(jù)失效),比如:

Response.Cache.SetExpires(DateTime.Now)

這可以清除緩存,但頁(yè)面上并不立刻體現(xiàn)出來(lái),直到最初的緩存期結(jié)束,比如:

%@ OutputCache Duration="10" VaryByParam="none" %>指令指定的緩存只會(huì)在10秒后才清除。通常并不需要清除所有緩存項(xiàng),你只要重新加載數(shù)據(jù)更新緩存就夠了。

2.1.2  輸出緩存(Output Cache)
你可以使用兩種方式的輸出緩存來(lái)緩存需要傳輸和顯示到客戶端瀏覽器上的數(shù)據(jù)——頁(yè)面輸出緩存(Page Output Cache)和頁(yè)面片斷緩存(Page Fragment Cache)。當(dāng)整個(gè)頁(yè)面相對(duì)變化較少時(shí),可以緩存整個(gè)頁(yè)面;如果只是頁(yè)面的一部分經(jīng)常變化,可以使用片斷緩存。

2.1.2.1 頁(yè)面輸出緩存
Page Output Caching將對(duì)頁(yè)面請(qǐng)求的響應(yīng)放入緩存中,后續(xù)對(duì)此頁(yè)面的請(qǐng)求將直接從緩存中得到信息而不是重建此頁(yè)面??梢酝ㄟ^(guò)添加Page指令(高級(jí)別,聲明實(shí)現(xiàn))來(lái)實(shí)現(xiàn),也可以使用HTTPCachePolicy類來(lái)實(shí)現(xiàn)(低級(jí)別,程序?qū)崿F(xiàn))。本指南不打算介紹技術(shù)細(xì)節(jié),只給出如何更好使用的指南和最佳實(shí)踐。有四方面的內(nèi)容:

1、決定緩存的內(nèi)容

頁(yè)面輸出緩存可緩存各種信息,緩存這些信息意味著你不需要經(jīng)常處理同樣的數(shù)據(jù)和結(jié)果,包括:

·經(jīng)常被請(qǐng)求但不不改變的靜態(tài)頁(yè)面;

·更新頻率和時(shí)間已知的頁(yè)面(如顯示股票價(jià)格的頁(yè)面);

·根據(jù)HTTP參數(shù),有幾個(gè)可能輸出的頁(yè)面(如根據(jù)城市的代號(hào)顯示該城市天氣情況的頁(yè)面);

·從Web Service返回的結(jié)果;如:

[WebMethod(CacheDuration=60)]

public string HelloWorld()

{

return "Hello World";

}

2、緩存動(dòng)態(tài)頁(yè)面

基于輸入?yún)?shù)、語(yǔ)言和瀏覽器類型改變的動(dòng)態(tài)網(wǎng)頁(yè)經(jīng)常用到。你可以使用OutputCache的以下屬性來(lái)實(shí)現(xiàn)對(duì)動(dòng)態(tài)頁(yè)面的緩存:

VaryByParam——基于輸入?yún)?shù)不同緩存同一頁(yè)面的多個(gè)版本;

VaryByHeader——基于Page Header的內(nèi)容不同緩存頁(yè)面的多個(gè)版本;

VaryByCustom——通過(guò)聲明屬性和重載GetVaryByCustomString方法來(lái)定制緩存處理頁(yè)面的多個(gè)版本;

VaryByControl——基于控件中asp對(duì)象屬性的不同來(lái)緩存控件。

對(duì)多個(gè)版本頁(yè)面的緩存會(huì)降低可用內(nèi)存,所以要仔細(xì)衡量緩存策略。s

3、控制緩存的位置

你可以使用@OutputCache指令的OutputCacheLocation屬性的枚舉值來(lái)指定緩存的位置,如:

%@ outputcache duration="10" varybyparam="none" Location="Server" %>

4、 配置頁(yè)面輸出緩存

有兩種方式控制,你可以使用Page指令,也可以使用Cache API編程實(shí)現(xiàn)。參考以下兩段代碼:

//代碼1,使用指令

%@ OutputCache Duration="20" Location="Server" VaryByParam="state" VaryByCustom="minorversion" VaryByHeader="Accept-Language"%>

//代碼2,編程實(shí)現(xiàn)

private void Page_Load(object sender, System.EventArgs e)

{

// Enable page output caching.

Response.Cache.SetCacheability(HttpCacheability.Server);

// Set the Duration parameter to 20 seconds.

Response.Cache.SetExpires(System.DateTime.Now.AddSeconds(20));

// Set the Header parameter.

Response.Cache.VaryByHeaders["Accept-Language"] = true;

// Set the cached parameter to 'state'.

Response.Cache.VaryByParams["state"] = true;

// Set the custom parameter to 'minorversion'.

Response.Cache.SetVaryByCustom("minorversion");

…

}

2.1.2.2 頁(yè)面片斷緩存
有時(shí)候緩存整個(gè)頁(yè)面并不靈活,同時(shí)內(nèi)存的發(fā)但也比較大,這時(shí)候應(yīng)考慮片斷緩存。頁(yè)面片斷緩存適合以下類型的數(shù)據(jù):

·創(chuàng)建開(kāi)銷很大的頁(yè)面片斷(控件);

·包含靜態(tài)數(shù)據(jù)的頁(yè)面片斷;

·可被多個(gè)用戶使用的頁(yè)面片斷;

·多個(gè)頁(yè)面共享的頁(yè)面片斷(如公用菜單條)

以下是緩存部分頁(yè)面的例子:

// Partial caching for 120 seconds

[System.Web.UI.PartialCaching(120)]

public class WebUserControl : System.Web.UI.UserControl

{

// Your Web control code

}

2.1.3  在非Web項(xiàng)目中使用Asp.net緩存
Asp.net Cache位于System.Web命名空間,但由于它是一個(gè)通用的方案,所以仍然可以在引用此命名空間的任何非Web項(xiàng)目中使用它。

System.Web.Caching.Cache 類是對(duì)象的緩存,它可以通過(guò)System.Web.HttpRuntime.Cache 的靜態(tài)屬性或System.Web.UI.Page 和System.Web.HttpContext.Cache來(lái)訪問(wèn)。因此在請(qǐng)求上下文之外也可以存在,在每個(gè)應(yīng)用程序域中只有一個(gè)實(shí)例,所以HttpRuntime.Cache對(duì)象可以在Aspnet_wp.exe之外的每個(gè)應(yīng)用程序域中存在。以下代碼演示了在普通應(yīng)用里訪問(wèn)Cache對(duì)象:

HttpRuntime httpRT = new HttpRuntime();

Cache cache = HttpRuntime.Cache; 

2.2 使用Remoting Singleton緩存
.Net Remoting提供了跨應(yīng)用程序域、跨進(jìn)程、跨計(jì)算機(jī)的程序運(yùn)行框架。服務(wù)器激活的對(duì)象有兩種激活模式,其中Singleton 類型任何時(shí)候都不會(huì)同時(shí)具有多個(gè)實(shí)例。如果存在實(shí)例,所有客戶端請(qǐng)求都由該實(shí)例提供服務(wù)。如果不存在實(shí)例,服務(wù)器將創(chuàng)建一個(gè)實(shí)例,而所有后繼的客戶端請(qǐng)求都將由該實(shí)例來(lái)提供服務(wù)。由于 Singleton 類型具有關(guān)聯(lián)的默認(rèn)生存期,即使任何時(shí)候都不會(huì)有一個(gè)以上的可用實(shí)例,客戶端也不會(huì)總接收到對(duì)可遠(yuǎn)程處理的類的同一實(shí)例的引用。所以將數(shù)據(jù)緩存起來(lái)可以在多個(gè)客戶端之間共享狀態(tài)信息。

為了使用.Net Remoting實(shí)現(xiàn)緩存方案,要保證遠(yuǎn)程對(duì)象的租約不過(guò)期,并且遠(yuǎn)程對(duì)象沒(méi)有被垃圾回收器銷毀(對(duì)象租約是指在系統(tǒng)刪除該對(duì)象前它在內(nèi)存中的生存期)。當(dāng)實(shí)現(xiàn)緩存時(shí),重載MarshalByRefObject的InitializeLifetimeService方法并且返回null,這樣就能保證租約永遠(yuǎn)不過(guò)期并且相關(guān)的對(duì)象生存期是無(wú)限的。以下代碼是一個(gè)示例:

public class DatasetStore : MarshalByRefObject

{

// A hash table-based data store

private Hashtable htStore = new Hashtable();

//Returns a null lifetime manager so that GC won't collect the object

public override object InitializeLifetimeService() { return null; }

// Your custom cache interface

}

注意:由于這種方案的成本較高、性能上的限制并且可能造成系統(tǒng)不穩(wěn)定,通常采用基于Sql Server的方案來(lái)替代。

2.3  使用內(nèi)存映射文件(Memory-Mapped File)
內(nèi)存映射文件提供獨(dú)一無(wú)二的特性,允許應(yīng)用程序通過(guò)指針來(lái)訪問(wèn)磁盤(pán)上的文件——與訪問(wèn)動(dòng)態(tài)內(nèi)存趣的方式一樣。所以你可以將應(yīng)用程序進(jìn)程中的某個(gè)地址段的數(shù)據(jù)映射到文件中,供多個(gè)跨應(yīng)用程序域或跨進(jìn)程訪問(wèn)。

在windows中,代碼和數(shù)據(jù)是以以種方式處理的,表現(xiàn)形式都是內(nèi)存頁(yè),而在內(nèi)存頁(yè)背后都是磁盤(pán)上的文件。唯一的不同磁盤(pán)上的文件類型不同。代碼后面是可執(zhí)行的鏡像,而數(shù)據(jù)后面則是系統(tǒng)的頁(yè)面文件。當(dāng)多個(gè)應(yīng)用程序共享內(nèi)存時(shí),系統(tǒng)的性能會(huì)有明顯提升。

你可以使用內(nèi)存映射文件的這種特性來(lái)實(shí)現(xiàn)同一臺(tái)機(jī)器上的跨進(jìn)程和跨應(yīng)用程序域的緩存解決方案?;趦?nèi)存映射文件的緩存方案包含以下組件:

·windows NT服務(wù)——啟動(dòng)時(shí)創(chuàng)建內(nèi)存映射文件,停止時(shí)刪除它。功能是向使用緩存的進(jìn)程提供句柄。當(dāng)然,也可以使用命名的內(nèi)存映射文件來(lái)提供操作接口;

·緩存托管組件(Cache Management Dll)——實(shí)現(xiàn)特定的緩存功能,比如:

a. 插入和刪除數(shù)據(jù)項(xiàng)到緩存中;

b. 使用算法清除緩存,比如最后使用算法(Least Recently Used);

c.  保證數(shù)據(jù)不被篡改;

基于內(nèi)存映射文件的緩存方案可以用在應(yīng)用程序的每個(gè)層中,但由于使用win32 API調(diào)用,所以并不容易實(shí)現(xiàn)。.Net 框架不支持內(nèi)存映射文件,所以只能以非托管代碼的方式運(yùn)行,當(dāng)然也不能利用.Net框架的有力特性,比如垃圾回收等。同時(shí)緩存數(shù)據(jù)項(xiàng)的管理功能需要定制開(kāi)發(fā),還要開(kāi)發(fā)性能計(jì)數(shù)器來(lái)監(jiān)控緩存的效果。

2.4使用SQL Server緩存
如果需要在進(jìn)程回收(重啟)、機(jī)器重啟或電源故障的過(guò)程中保持緩存數(shù)據(jù)的有效,基于內(nèi)存的方案并不能滿足要求。你可以使用基于永久數(shù)據(jù)存儲(chǔ)的方案,如SQL server數(shù)據(jù)庫(kù)或NTFS文件系統(tǒng)。

SQL Server在使用sql語(yǔ)句或存儲(chǔ)過(guò)程得到數(shù)據(jù)時(shí),對(duì)varchar和varBinary類型的數(shù)據(jù)有8k的大小限制,你必須使用.Net 框架提供的Ado.Net SQLDataAdapter對(duì)象來(lái)訪問(wèn)datatable或dataset。

使用SQL Server緩存數(shù)據(jù)的優(yōu)點(diǎn):

·易于實(shí)現(xiàn)——使用.Net 框架和Ado.Net訪問(wèn)數(shù)據(jù)庫(kù)相當(dāng)方便;

·完善的安全模型和很高的健壯性;

·數(shù)據(jù)非常方便的共享;

·數(shù)據(jù)的持久保留。

·支持很大的數(shù)據(jù)量。

·方便的管理工具

當(dāng)然,也有缺點(diǎn):

·需要安裝SQL Server,對(duì)小型應(yīng)用來(lái)說(shuō)不合適;

·重新構(gòu)造數(shù)據(jù)的性能和讀取數(shù)據(jù)庫(kù)的性能比較;

·網(wǎng)絡(luò)負(fù)擔(dān)。

2.5 使用靜態(tài)變量緩存
靜態(tài)變量常用來(lái)記錄類的狀態(tài),你可以用它來(lái)創(chuàng)建定制的緩存對(duì)象。在定制的緩存類中將你的數(shù)據(jù)存儲(chǔ)器聲明為靜態(tài)變量,并且提供維護(hù)接口(插入、刪除和訪問(wèn)等)。如果沒(méi)有特殊的緩存需求(比如依賴、失效策略等),使用靜態(tài)變量緩存數(shù)據(jù)是很方便的。由于是在內(nèi)存中,這種方案可提供對(duì)緩存數(shù)據(jù)的直接、高速的訪問(wèn),當(dāng)沒(méi)有替代方案解決鍵值對(duì)的存儲(chǔ)且對(duì)速度要求很高時(shí),可以使用靜態(tài)變量。當(dāng)然,在asp.net中,應(yīng)該使用Cache對(duì)象。

你可以使用這種方案保存大數(shù)據(jù)的對(duì)象,前提是它不經(jīng)常更改。由于沒(méi)有清除機(jī)制,大數(shù)據(jù)的內(nèi)存消耗會(huì)影響性能。

你需要保證定制線程安全機(jī)制,或者使用.Net框架提供的同步對(duì)象,比如Hashtable。以下代碼是使用Hashtable實(shí)現(xiàn)的例子:

static Hashtable mCacheData = new Hashtable();

應(yīng)用范圍:本方案的應(yīng)用范圍可以限制到類、模塊或整個(gè)項(xiàng)目。如果變量定義為public,整個(gè)項(xiàng)目中的代碼都能訪問(wèn)它,范圍是整個(gè)應(yīng)用程序域,實(shí)現(xiàn)了高效的共享。而它的生存期是和范圍緊密相關(guān)的。

2.6 使用asp.net session state
你可以使用基于HttpSessionState對(duì)象的asp.net session state來(lái)緩存單個(gè)用戶的會(huì)話狀態(tài)信息。它解決了asp中會(huì)話狀態(tài)的很多限制,包括:

·asp session要求客戶端接受cookies,否則就不能使用session;而asp.net可以配置為不使用cookie;

·對(duì)web server場(chǎng)的情況,asp的session不能支持;當(dāng)穩(wěn)定性和可用性要求很高時(shí),asp.net session state雖然效果不好,但對(duì)比較小的單個(gè)值scalar Value(比如登錄信息),還是很有效。

Asp.net session有很大改進(jìn),下面描述使用范圍和使用方式。

Asp.net session state有三種操作模式:

1、進(jìn)程內(nèi)模式InProc——Session State信息在asp.net工作進(jìn)程aspnet_wp.exe的進(jìn)程的內(nèi)存中存儲(chǔ)。這是默認(rèn)選項(xiàng),這種情況下,如果進(jìn)程或應(yīng)用程序域被回收,則Session 狀態(tài)信息也被回收;

2、進(jìn)程外模式State Server——狀態(tài)信息序列化后保存在獨(dú)立的狀態(tài)進(jìn)程中(AspNet_State.exe),所以狀態(tài)信息可以保存在專門(mén)的服務(wù)器上(一個(gè)狀態(tài)服務(wù)器State Server);

3、 Sql server模式——狀態(tài)信息序列化后保存在SQL Server數(shù)據(jù)庫(kù)中。

你可以通過(guò)調(diào)整配置文件中sessionState>標(biāo)簽的mode屬性來(lái)設(shè)置要使用的狀態(tài)模式,比如使用SQL Server模式來(lái)在Web server場(chǎng)中共享狀態(tài)信息。當(dāng)然,這個(gè)優(yōu)勢(shì)也有缺點(diǎn),就是狀態(tài)信息需要序列化和反序列化,同時(shí)多了對(duì)數(shù)據(jù)庫(kù)的寫(xiě)入和讀取,所以性能上有開(kāi)銷,這是要仔細(xì)評(píng)估的。

2.6.1  選擇使用模式
2.6.1.1 使用InProc模式
當(dāng)使用進(jìn)程內(nèi)模式時(shí),狀態(tài)信息保存在aspnet_wp.exe的進(jìn)程中。由于在web場(chǎng)的情況下aspnet_wp.exe的多個(gè)實(shí)例在同一臺(tái)服務(wù)器上運(yùn)行,所以進(jìn)程內(nèi)模式不適用與web場(chǎng)的情況。

進(jìn)程內(nèi)模式是唯一支持Session_End事件的session模式,當(dāng)用戶會(huì)話超時(shí)或中止時(shí),可以運(yùn)行Session_End中的事件處理代碼來(lái)清除資源。

2.6.1.2 使用StateServer模式
StateServer模式使用指定的進(jìn)程儲(chǔ)存狀態(tài)信息。因?yàn)樗彩且环N進(jìn)程外模式,所以要保證你存儲(chǔ)的對(duì)象是可序列化的,以支持跨進(jìn)程傳輸。

當(dāng)使用Session對(duì)象在web場(chǎng)的情況下使用時(shí),必須保證web.config文件中的MachineKey>元素在所有服務(wù)器上是唯一的。這樣所有的服務(wù)器使用同樣的加密方式,才能訪問(wèn)緩存中的數(shù)據(jù)。參考msdn中的“MachineKey元素”。

2.6.1.3 使用SQL Server模式
SQL Server模式下,當(dāng)你使用信任連接(trusted_connection=true 或 integrated security=sspi)訪問(wèn)Session state信息時(shí),不能在asp.net中使用身份用戶模擬。

默認(rèn)情況下,SQL Server將狀態(tài)信息存儲(chǔ)在TempDb數(shù)據(jù)庫(kù)中,它在每次Sql server服務(wù)啟動(dòng)時(shí)會(huì)自動(dòng)重新創(chuàng)建,當(dāng)然,你可以指定自己的數(shù)據(jù)庫(kù)以便在數(shù)據(jù)庫(kù)重啟的過(guò)程中也能保持?jǐn)?shù)據(jù)。

2.6.2  決定使用Session對(duì)象要存儲(chǔ)的內(nèi)容
你可以使用Session對(duì)象緩存任何類型的.net框架數(shù)據(jù),但是要了解對(duì)某種類型來(lái)說(shuō)最好的方式是什么。有以下幾點(diǎn)需要說(shuō)明:

1、  對(duì)基本類型(比如Int,Byte,String)來(lái)說(shuō),可以使用任何方式。因?yàn)樵谶x用進(jìn)程外方式時(shí),asp.net使用一個(gè)優(yōu)化的內(nèi)部方法來(lái)序列化和反序列化基本類型的數(shù)據(jù);

2、  對(duì)復(fù)雜類型(如ArrayList)來(lái)說(shuō),只選用進(jìn)程內(nèi)方式。因?yàn)閍sp.net使用BinaryFormatter來(lái)序列化和反序列化這類數(shù)據(jù),而這會(huì)影響性能的。當(dāng)然,只有在State Server和SQL Server的方式下,才會(huì)進(jìn)行序列化操作;

3、  緩存的安全問(wèn)題,當(dāng)在緩存中存儲(chǔ)敏感數(shù)據(jù)時(shí),需要考慮安全性,其它頁(yè)面可以訪問(wèn)到緩存中的數(shù)據(jù);

4、  避免緩存大數(shù)據(jù),那會(huì)降低性能;

5、  這種緩存方式不支持過(guò)期策略、清除和依賴。

2.6.3  實(shí)現(xiàn)Session State
Asp.net提供了簡(jiǎn)單接口來(lái)操作Session State,并可使用Web.Config進(jìn)行簡(jiǎn)單設(shè)置,當(dāng)配置文件中的設(shè)置改變時(shí),能夠在頁(yè)面上立刻體現(xiàn)出來(lái),而不需要重新啟動(dòng)asp.net進(jìn)程。

以下代碼演示了使用SQL Server來(lái)實(shí)現(xiàn)Session數(shù)據(jù)的存儲(chǔ)和使用。

sessionState

mode="SQLServer"

stateConnectionString="tcpip=127.0.0.1:42424"

sqlConnectionString="data source=127.0.0.1; Integrated Security=SSPI"

cookieless="false"

timeout="20"

/>

private void SaveSession(string CartID)

{

Session["ShoppingCartID"] = CartID;

}

private void CheckOut()

{

string CartID = (string)Session["ShoppingCartID"];

if(CartID != null)

{

// Transfer execution to payment page.

Server.Transfer("Payment.aspx");

}

else

{

// Display error message.

}

}

2.7使用Asp.net客戶端緩存和狀態(tài)
你還可以使用客戶端存儲(chǔ)頁(yè)面信息的方式來(lái)降低服務(wù)器的負(fù)擔(dān),這種方法提供最低的安全保障,但卻有最快的性能表現(xiàn)。由于需要將數(shù)據(jù)發(fā)送到客戶端存儲(chǔ),所以數(shù)據(jù)量有限。

實(shí)現(xiàn)客戶端緩存的機(jī)制有以下五種,接下來(lái)將依次介紹:

·隱藏欄位(Hidden Field)

·View State

·隱藏幀(Hidden Frame)

·Cookies

·Query String

這五種方式分別適合于存儲(chǔ)不同類型的數(shù)據(jù)。

2.7.1  使用Hidden Field
你可以將經(jīng)常改變的少量數(shù)據(jù)保存在HtmlInputHidden中來(lái)維護(hù)頁(yè)面的狀態(tài)。當(dāng)每次頁(yè)面回送的過(guò)程中,這些數(shù)據(jù)都會(huì)包含在表單中大送到服務(wù)器,所以你要使用HTTP POST方式來(lái)提交頁(yè)面。

使用這種方式的優(yōu)點(diǎn)如下:

不需要服務(wù)器資源,直接從頁(yè)面中讀取;
幾乎所有的瀏覽器都支持;
實(shí)現(xiàn)簡(jiǎn)單;
由于數(shù)據(jù)在頁(yè)面中,所以在web Farm的情況下也可使用。
缺點(diǎn):

由于可以通過(guò)查看源碼看到,所以可能會(huì)被篡改;
不支持復(fù)雜格式的數(shù)據(jù),復(fù)雜數(shù)據(jù)必須使用解析字符串的方式來(lái)間接得到;
當(dāng)存儲(chǔ)大數(shù)據(jù)的時(shí)候會(huì)影響性能。
示例:

input id="HiddenValue" type="hidden" value="Initial Value" runat="server" NAME="HiddenValue">

2.7.2  使用View State
所有的Web Form頁(yè)面和控件都包含有一個(gè)ViewState屬性,在對(duì)同一頁(yè)面多次請(qǐng)求時(shí)可以保持頁(yè)面內(nèi)的值。它的內(nèi)部實(shí)現(xiàn)是維護(hù)相應(yīng)的hidden field,只不過(guò)是加密了的,所以比hidden field的安全性要好。

使用View State的性能表現(xiàn)很大程度上依賴于服務(wù)器控件的類型。一般來(lái)說(shuō),Label,TextBox,CheckBox,RadioButton,HyperLink的性能要好一些,而DropdownList,ListBox,DataGrid和DataList就要差很多,因?yàn)榘臄?shù)據(jù)量太大,所以每次頁(yè)面回送都很耗時(shí)間。

有些情況下不推薦使用ViewState,比如:

1、不需要回送的頁(yè)面避免使用;

2、避免使用ViewState保存大數(shù)據(jù)量;

3、在需要使用會(huì)話超時(shí)的情況下避免使用它,因?yàn)樗鼪](méi)有超時(shí)操作。

ViewState的性能表現(xiàn)和Hidden Field的是類似的,但是具有更高的安全性。

優(yōu)點(diǎn):

數(shù)據(jù)在頁(yè)面中自動(dòng)維護(hù),不需要服務(wù)器資源;
實(shí)現(xiàn)簡(jiǎn)單;
數(shù)據(jù)是經(jīng)過(guò)加密和壓縮的,比hidden field有更高的安全性;
數(shù)據(jù)存在客戶端,可以在Web Farm情況下使用。

缺點(diǎn):

存儲(chǔ)大數(shù)據(jù)量時(shí)會(huì)降低性能;
和hidden field類似,在客戶端數(shù)據(jù)仍然有潛在的安全威脅。
示例代碼如下:

public class ViewStateSample : System.Web.UI.Page

{

private void Page_Load(object sender, System.EventArgs e)

{

if (!Page.IsPostBack)

{

// Save some data in the ViewState property.

this.ViewState["EnterTime"] = DateTime.Now.ToString();

this.ViewState["UserName"] = "John Smith";

this.ViewState["Country"] = "USA";

}

}

…

private void btnRefresh_Click(object sender, System.EventArgs e)

{

// Get the saved data in the view state and display it.

this.lblTime.Text = this.ViewState["EnterTime"].ToString();

this.lblUserName.Text = this.ViewState["UserName"].ToString();

this.lblCountry.Text = this.ViewState["Country"].ToString();

}

}

2.7.3  使用Hidden Frame
你可以使用Hidden Frame在客戶端緩存數(shù)據(jù),這就避免了使用hidden field和使用view state時(shí)每次頁(yè)面回送時(shí)的緩存數(shù)據(jù)往返。比如你可以秘密的加載多個(gè)頁(yè)面所需要的圖片,這并不會(huì)消耗服務(wù)器資源。

優(yōu)點(diǎn):

a. 可以加載較多數(shù)據(jù)而不只是單個(gè)欄位的值;

b. 避免了不必要的多次回送中的數(shù)據(jù)往來(lái);

c.可以緩存和讀取在不同表單中存儲(chǔ)的數(shù)據(jù)項(xiàng)(可以同時(shí)緩存多個(gè)頁(yè)面的數(shù)據(jù));

d.可以訪問(wèn)同一站點(diǎn)不同frame中的客戶端腳本數(shù)據(jù)。

缺點(diǎn):

a. 有些瀏覽器不支持frame;

b. 源代碼可以在客戶端看到,有潛在的安全威脅;

c. 隱藏frame的數(shù)量沒(méi)有限制,如果框架頁(yè)面包含較多hidden frame的話,在首次加載時(shí)速度會(huì)有限制。

示例代碼如下:

FRAMESET cols="100%,*">

FRAMESET rows="100%,*">

FRAME src="contents_of_frame1.html">

/FRAMESET>

FRAME src="contents_of_hidden_frame.html">

FRAME src="contents_of_hidden_frame.html" frameborder="0" noresize scrolling="yes">

NOFRAMES>

P>This frameset document contains:

A href="contents_of_frame1.html" TARGET="_top">Some neat contents/A>

/NOFRAMES>

/FRAMESET>

2.7.4  使用Cookies
Cookie是可以在客戶端存儲(chǔ)數(shù)據(jù)另一種方案,這里不過(guò)多介紹。

優(yōu)點(diǎn):

不需要服務(wù)器資源;數(shù)據(jù)保存在客戶端,在用戶請(qǐng)求時(shí)發(fā)送到服務(wù)器上。
使用簡(jiǎn)單。Cookie包含簡(jiǎn)單的鍵值對(duì),主要保存輕量級(jí)的文本數(shù)據(jù)。
支持過(guò)期策略;可以指定當(dāng)會(huì)話結(jié)束時(shí)過(guò)期,也可指定一個(gè)時(shí)間策略。

缺點(diǎn):

數(shù)據(jù)量的限制;
用戶可能設(shè)置為拒絕Cookie;
安全問(wèn)題;用戶可能更改機(jī)器上的cookie信息,造成基于cookie的系統(tǒng)運(yùn)行失??;
可能過(guò)期或被用戶刪除,造成一定程度的不可用。
參看示例代碼:

public class CookiesSample : System.Web.UI.Page

{

private void Page_Load(object sender, System.EventArgs e)

{

if (this.Request.Cookies["preferences1"] == null)

{

HttpCookie cookie = new HttpCookie("preferences1");

cookie.Values.Add("ForeColor","black");

cookie.Values.Add("BackColor","beige");

cookie.Values.Add("FontSize","8pt");

cookie.Values.Add("FontName","Verdana");

this.Response.AppendCookie(cookie);

}

}

private string getStyle(string key)

{

string val = null;

HttpCookie cookie= this.Request.Cookies["preferences1"];

if (cookie != null)

{

val = cookie.Values[key];

}

return val;

}

}

2.7.5  使用Query String
Query String是在用戶請(qǐng)求的URL后加上相應(yīng)的參數(shù)來(lái)使用的,只能在使用HTTP GET方式調(diào)用URL時(shí)可用。

優(yōu)點(diǎn):

d.不需要服務(wù)器資源,參數(shù)附在URL里面;

e. 應(yīng)用面廣,幾乎所有瀏覽器都支持;

f.實(shí)現(xiàn)簡(jiǎn)單,服務(wù)端使用Request對(duì)象可直接讀取。

缺點(diǎn):

a.參數(shù)直接對(duì)用戶可見(jiàn),不安全;

b.URL長(zhǎng)度的限制,多數(shù)瀏覽器不支持超過(guò)255字符的URL。

示例代碼:

string user = Request.QueryString["User"];

2.7.6  小結(jié)
下表是使用客戶端緩存的建議:

2.8 使用Internet Explorer緩存
IE提供了緩存機(jī)制,可以實(shí)現(xiàn)對(duì)頁(yè)面的數(shù)據(jù)進(jìn)行緩存,同時(shí)可以指定過(guò)期時(shí)間。用戶在IE中請(qǐng)求此頁(yè)面,如果當(dāng)過(guò)期時(shí)間沒(méi)有到,則自動(dòng)從緩存中提取并呈現(xiàn);否則,就到服務(wù)器上獲取新版本。IE對(duì)頁(yè)面的緩存可以在IIS中設(shè)置。

適合在Internet Explorer中緩存的內(nèi)容

頁(yè)面中的圖像文件;
靜態(tài)的文本內(nèi)容;
頁(yè)面的標(biāo)題欄和頁(yè)腳內(nèi)容——改變頻率很低,可以給用戶一個(gè)迅速相應(yīng);
網(wǎng)站的首頁(yè)——更改次數(shù)頁(yè)時(shí)相對(duì)較少的;
使用動(dòng)態(tài)HTML在客戶端保存的特定數(shù)據(jù),比如客戶自定義的顏色和布局設(shè)置信息。

優(yōu)點(diǎn):

減少對(duì)服務(wù)器的請(qǐng)求和網(wǎng)絡(luò)負(fù)擔(dān);
支持離線瀏覽;
可以實(shí)現(xiàn)基于XML的客戶端復(fù)雜應(yīng)用。

缺點(diǎn):

客戶端的過(guò)期時(shí)間必須預(yù)先指定而不能依賴于服務(wù)器更新;IE采用的是Lazy更新機(jī)制,優(yōu)先從緩存中提取數(shù)據(jù);
對(duì)其它客戶端瀏覽器沒(méi)有作用;
存儲(chǔ)的數(shù)據(jù)沒(méi)有加密,不能保證客戶端數(shù)據(jù)安全。
示例代碼:

META HTTP-EQUIV="expires" CONTENT="Tue, 23 Jun 2002 01:46:05 GMT">

本文介紹了緩存和狀態(tài)數(shù)據(jù)存儲(chǔ)的相關(guān)概念,以及可供使用的緩存技術(shù),介紹了各種技術(shù)的適用范圍,并對(duì)其優(yōu)缺點(diǎn)進(jìn)行了說(shuō)明,另外有簡(jiǎn)單的性能比較和簡(jiǎn)單的示例代碼。

以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助。

您可能感興趣的文章:
  • asp.net(C#)遍歷memcached緩存對(duì)象
  • asp.net 使用駐留在頁(yè)面中的Cache緩存常用可定時(shí)更新的數(shù)據(jù)
  • asp.net下Cache 緩存操作類代碼
  • asp.net開(kāi)發(fā)中怎樣去突破文件依賴緩存
  • ASP.NET性能優(yōu)化之讓瀏覽器緩存動(dòng)態(tài)網(wǎng)頁(yè)的方法
  • asp.net中Session緩存與Cache緩存的區(qū)別分析
  • ASP.NET頁(yè)面在IE緩存的清除辦法
  • 設(shè)置ASP.NET頁(yè)面不被緩存(客戶端/服務(wù)器端取消緩存方法)
  • .net/c# memcached緩存獲取所有緩存鍵的方法步驟
  • Asp.net禁用頁(yè)面緩存的方法總結(jié)

標(biāo)簽:本溪 汕頭 吉林 宜春 重慶 河南 麗江 婁底

巨人網(wǎng)絡(luò)通訊聲明:本文標(biāo)題《全面剖析.Net環(huán)境下的緩存技術(shù)》,本文關(guān)鍵詞  全面,剖析,.Net,環(huán)境,下,;如發(fā)現(xiàn)本文內(nèi)容存在版權(quán)問(wèn)題,煩請(qǐng)?zhí)峁┫嚓P(guān)信息告之我們,我們將及時(shí)溝通與處理。本站內(nèi)容系統(tǒng)采集于網(wǎng)絡(luò),涉及言論、版權(quán)與本站無(wú)關(guān)。
  • 相關(guān)文章
  • 下面列出與本文章《全面剖析.Net環(huán)境下的緩存技術(shù)》相關(guān)的同類信息!
  • 本頁(yè)收集關(guān)于全面剖析.Net環(huán)境下的緩存技術(shù)的相關(guān)信息資訊供網(wǎng)民參考!
  • 推薦文章