要提升ASP.NET应用程序的性能,最简单、最有效的方式就是使用内建的缓存引擎。虽然也能构建自己的缓存,但由于缓存引擎已提供了如此多的功能,所以完全不必如此麻烦。在很大程度上,ASP.NET开发者在Web应用程序中,能将缓存引擎的功能直接包装到自己的数据表示及访问类中。如本文所述,整个过程其实非常简单。
ASP.NET的缓存引擎支持三种类型的缓存:
整页输出缓存是在一个页被首次请求时,将整个页呈现好的HTML内容缓存下来。后续请求将直接取用缓存拷贝。
部分缓存是指缓存一部分HTML内容,这类似一个Web用户控件的输出。之所以叫这样的一个名字,是因为我们一般说“将一部分HTML提交给一个页”。
数据缓存关注的是单独的变量或数据项的缓存。它在比以上两种缓存类型都要低的一个级别上工作。

整页输出缓存

整页输出缓存是最简单的缓存类型,它只要求为准备缓存的页添加一个预处理指令OutputCache。使用这种缓存,就不必重新处理一个页的Init,Load,PreRender,Render以及Unload事件。假如那些事件要访问像数据库那样的一个后端系统,那么节省的时间将是非常可观的。ASP.NET可缓存一个页的几个变体,并将每个页都与后续请求相关联。所有这些都由OutputCache预处理指令来控制,该命令要放在一个ASPX页的顶部,并采用以下格式:
<%@ OutputCache
Duration="#ofseconds"
Location="Any | Client | Downstream | Server | None"
VaryByCustom="browser | customstring"
VaryByHeader="headers"
VaryByParam="parameter name" %>
OutputCache预处理指令最多可利用5个相关的属性来控制缓存行为。表A总结了这些属性及其含义。

表A属性说明 
Duration 该属性指定了网页要缓存的时间(以秒为单位)。通过为一个页设置该属性,可为来自对象HTTP响应建立一个过期策略。这是一个必需属性。如果不包括它,会发生解析器错误。注意它指定的是绝对过期时间,而非周期性过期。 
Location 用这个属性指示Web服务器和下游设备(比如代理服务器和浏览器)来缓存页面内容。默认为Any,该属性并非必需的。 
VaryByParam 该属性使用由分号分隔的字符串列表来改变输出缓存。默认情况下,这些字符串对应于随GET方法属性发送的查询字符串值,或对应于使用POST方法发送的一个参数。如果将该属性设为多个参数,输出缓存将针对指定的每个参数,包含所请求的文档的一个不同版本。可能的值包括None、*以及任何有效的查询字符串或POST参数名。如果没有设置其他属性,该属性就是必需的。 
VaryByCustom 对自定义输出缓存需求进行表示的任何文本都要包含在这个属性中。如果为属性指派浏览器的一个值,缓存会根据浏览器名称及主版本信息而发生变化。如果输入一个自定义字符串,就必须在应用程序的Global.asax文件中覆盖GetVaryByCustomString方法。 
VaryByHeader 该属性使用由分号分隔的HTTP标头列表来改变输出缓存。如果属性设为多个标头,输出缓存将针对指定的每个标头,包含所请求文档的一个不同的版本。

OutputCache属性
OutputCache预处理指令可在内存中方便地创建静态页的单一版本,例如:
<%@ OutputCache Duration=“300" VaryByParam="None" %>
还可根据id查询字符串参数来缓存多个版本,例如:
<%@ OutputCache Duration=“300" VaryByParam="id" %>
在上述两个例子中,网页会在5分钟(300秒)后从缓存中清除,该数字是由Duration属性指定的。

根据自定义信息来缓存
使用VaryByCustom属性,可根据你提供的自定义信息来创建一个页的缓存版本。例如,要为每种类型的浏览器创建网页的一个不同版本,可使用以下预处理指令:
<%@ OutputCache Duration=“300" VaryByParam="None" VaryByCustom=“browser”%>
使用VaryByCustom,还可根据应用程序特有的信息来缓存网页。例如,要根据当前用户的部门名称来创建网页的缓存版本,可使用以下预处理指令:
<%@ OutputCache Duration=“300" VaryByParam="None" VaryByCustom=“department”%>
然后,在用于Global.asax文件的代码隐藏类中,可覆盖GetVaryByCustomString方法,如以下VB.NET代码所示:
Public Overrides Function GetVaryByCustomString( _
ByVal context As System.Web.HttpContext, _
ByVal custom As String) As String
If custom = "department" Then
' return the department for the current user
End If
End Function
这里向GetVaryByCustomString方法传递了在预处理指令中使用的自定义值。ASP.NET运行库调用该方法时,你可使用自己的算法,根据输入值来判断当前用户所在的部门,并从方法中返回它。

根据标头信息来缓存

使用VaryByHeader属性,可根据网页接收到的一个或多个HTTP标头来创建一个网页的多个缓存版本。例如,要想根据浏览器的语言来创建和缓存不同的版本,可使用以下预处理指令:
<%@ OutputCache Duration="60" VaryByParam="None" VaryByHeader="Accept-Language" %>

检查标头
要查看随同特定Web请求发送的各个HTTP标头的值,可打开ASP.NET页的跟踪功能,具体做法是在网页的Page预处理指令中设置trace和traceMode属性。另外,也可通过Visual Studio .NET的属性页来设置。
除了声明性地缓存整个网页,还可使用由Page类揭示的Response对象的Cache属性来程序化地设置一个页的缓存选项。Cache属性揭示了用于网页的HttpCachePolicy对象,可用它在服务器上将缓存时间设为5分钟,如以下C# 代码段所示:
private void Page_Init( object sender, System.EventArgs e )

Response.Cache.SetCacheability(HttpCacheability.Server);
Response.Cache.SetExpires(DateTime.Now.AddSeconds(300));
Response.Cache.SetValidUntilExpires(True)
}

部分缓存

部分缓存允许只缓存部分HTML,它的效率很高,因为一个页中经常变化的部分可与那些不经常变化部分的部分合并到一起,同时仍能从缓存中检索静态的部分。一个实例是将“部分缓存”应用于需要调用XML Web服务的Web用户控件。这样可获得很高的效率,因为它避免了你的网站与Web服务过度紧密地耦合,同时还能显著提升性能。
要使用部分缓存,同样可在HTML页的顶部放置一条OutputCache预处理指令。但这一次,我们准备把它放到Web用户控件的ASCX页中。注意使用部分缓存时,Location和VaryByHeader属性将不再支持,但新增了对VaryByControl属性的支持。
使用VaryByControl属性,可用一个由分号分隔的列表来指定用户控件的一个或多个属性。可为属性值的每一种组合来创建缓存的版本。例如,假定你的用户控件揭示出一个自定义的State属性,它控制着要显示用户控件的哪些元素。使用以下预处理指令,可针对State的每个值来缓存控件所具体呈现的一个版本:
<%@ OutputCache Duration="300" VaryByControl="State" %>
但在缓存Web用户控件时,记住ASP.NET运行库会直接用缓存的HTML来替换实际控件,忽略平常会发生的任何控件处理。这暗示着在网页中执行的代码不能程序化地操纵一个缓存的用户控件或者它的任何属性。换言之,Web用户控件必须能完全自主,并能通过它的Load和Init事件来初始化自己,以便有效地捍妗?/P> 
也可声明性地完成部分缓存,方法是使用一个属性而不是使用OutputCache预处理指令。在代码隐藏文件中,PartialCaching属性可放在从UserControl派生的一个类中,使ASP.NET运行库能够读取它,并相应地缓存呈现好的HTML。例如,以下来自代码隐藏类的声明能根据查询字符串中的id值,将Web用户控件缓存5分钟。
<PartialCaching(300, "id", Nothing, Nothing)> _
Public MustInherit Class MyHeaderControl
Inherits System.Web.UI.UserControl

数据缓存
ASP.NET缓存引擎支持的最后一种缓存类型是“数据缓存”。根据定义,它的工作级别要低于整页输出缓存和部分缓存。假如几个网页都要使用相同的数据(例如一个产品列表),但要以不同方式来显示这些数据,就可考虑使用这种缓存。当然,数据缓存之所以具有性能优势,是因为减少了对后端数据库的调用次数。
为了在缓存中添加一个项,需使用Page或UserControl类的Cache属性,因为这两个类最终都是从Control类派生的。Cache属性揭示出了System.Web.Caching.Cache对象,利用它可将数据当作键和值的一个组合来存储。使用该属性,开发者可编写代码来填充一个项,并把它放到缓存中;如果该项已经存在,就直接将其从缓存中取出。如以下C#代码所示。
DataTable dt = null;
if (this.Cache["Products"] == null)
{
// Go get the data from the database
this.Cache.Insert("Products", dt, null, DateTime.Now.AddHours(6), TimeSpan.Zero);
}
else
{
dt = this.Cache["Products"] As DataTable;
}
上例首先检查具有Products键的项是否在缓存中。如果不在,就从后端数据库检索一个ADO.NET DataTable,并使用Insert方法把它放到缓存中。本例使用的是Insert的一个重载版本,它允许为缓存对象指定一个绝对过期时间(6小时),而不是指定一个周期性的过期。相反,如果缓存中已经有这个项,就将其取回,并使用As表达式,将其强制转换回一个DataTable。
对ADO.NET检索到的数据进行缓存时,注意既可像上例那样缓存DataTable对象,也可缓存整个DataSet对象,因为两种对象都同任何数据源完全地断开,不会保持数据库连接。对数据读取器(比如SqlDataReader)进行缓存似乎更好一些,因为它们只使用一次(它们是“只进”的读取器),而且在打开的情况下将一直占据一个数据库连接。
ASP.NET缓存引擎强大的灵活性和功能使其成为创建高性能ASP.NET应用程序时最重要的特性之一。根据本文提供的基本信息,你可在自己的应用程序轻松引入缓存引擎功能。

ASP.NET缓存策略经验谈的更多相关文章

  1. ASP.NET缓存中Cache过期的三种策略

    原文:ASP.NET缓存中Cache过期的三种策略 我们在页面上添加三个按钮并双击按钮创建事件处理方法,三个按钮使用不同的过期策略添加ASP.NET缓存. <asp:Button ID=&quo ...

  2. ASP.NET Cache 实现依赖Oracle的缓存策略

    ASP.NET 中的缓存提供了对SQL依赖项的支持,也就是说当SQL SERVER数据库中的表或行中的数据被更改后,缓存中的页面就失效,否则,页面输出可一直保留在缓存当中.这确实为程序员提供了方便.但 ...

  3. asp.net—缓存

    1.页面缓存 要实现页面输出缓存,只要将一条 OutputCache 指令添加到页面即可. <%@ OutputCache CacheProfile=" " NoStore= ...

  4. ASP.NET缓存全解析2:页面输出缓存 转自网络原文作者李天平

    页面输出缓存是最为简单的缓存机制,该机制将整个ASP.NET页面内容保存在服务器内存中.当用户请求该页面时,系统从内存中输出相关数据,直到缓存数据过期.在这个过程中,缓存内容直接发送给用户,而不必再次 ...

  5. Asp.Net缓存(2)

    缓存页的多个版本 ASP.NET 允许在输出缓存中缓存同一页的多个版本.输出缓存可能会因下列因素而异: 初始请求 (HTTP GET) 中的查询字符串. 回发时传递的控制值(HTTP POST 值). ...

  6. Asp.Net缓存(1)

    知其根本,方能应用.MSDN上的缓存讲解.先看原来讲解. Asp.Net缓存概述 通常,应用程序可以将那些频繁访问的数据,以及那些需要大量处理时间来创建的数据存储在内存中,从而提高性能. 在这些情况下 ...

  7. ASP.NET缓存 Cache

    缓存介绍 如果每次进入页面的时候都查询数据库生成页面内容的话,如果访问量非常大,则网站性能会非常差,而如果只有第一次访问的时候才查询数据库生成页面内容,以后都直接输出内容,则能提高系统性能,这样无论多 ...

  8. asp.net缓存(一)

    ASP.NET页面输出缓存(OutputCache) 页面输出缓存是最为简单的缓存机制,该机制将整个ASP.NET页面内容保存在服务器内存中.当用户请求该页面时,系统从内存中输出相关数据,直到缓存数据 ...

  9. ASP.NET - 缓存(Cache)

    页面缓存: 给页面添加<%@ OutPutCache Duration = “15” VaryByParam = “none” %> 这样就可以启用页面缓存了,那么在规定的时间内,页面之访 ...

随机推荐

  1. What is Object Oriented Design? (OOD)

    Object Oriented Design is the concept that forces programmers to plan out their code in order to hav ...

  2. MSVC CRT运行库启动代码分析

    原文链接:http://www.programlife.net/msvc-crt-startup.html 在程序进入main/WinMain函数之前,需要先进行C运行库的初始化操作,通过在Visua ...

  3. JsRender系列demo-10

    <!DOCTYPE html> <html> <head> <script src="http://code.jquery.com/jquery.j ...

  4. LR_问题_脚本运行时提示没有参数化

    问题描述 将loadrunner中的参数删除,并且删除脚本目录下对应的bak,执行脚本,出现下面的错误: “错误: 表“XX\phonenumbser.dat”不存在.         [MsgId: ...

  5. [图解教程]Eclipse不可不知的用法之一:自动生成Getter、Setter和构造方法

    [图解教程]Eclipse不可不知的用法之一:自动生成Getter.Setter和构造方法 关键词:Getters and Setters.getter和setter方法.Constructor us ...

  6. RunAsAdmin in windows 8

    function RunAsAdmin(hWnd: HWND; filename: string; Parameters: string): Boolean; { See Step 3: Redesi ...

  7. VIM Taglist + ctags

    Windows下 进入http://ctags.sourceforge.net/ 下载ctags 把ctags58.zip解压,随便放个地方,我放到了Home\Vim\vim72下,在ctags58文 ...

  8. Android ListView高度自适应和ScrollView冲突解决

    在ScrollView中嵌套使用ListView,ListView只会显示一行到两行的数据.起初我以为是样式的问题,一直在对XML文件的样式进行尝试性设置,但始终得不到想要的效果.后来在网上查了查,S ...

  9. JS代码片段:一个日期离现在多久了

    var dateDiff = function(hisTime,nowTime){ if(!arguments.length) return ''; var arg = arguments, now ...

  10. java--面向抽象编程

    所谓面向抽象编程是指当设计某种重要的类时,不让该类面向具体的类,而是面向抽象类,及所设计类中的重要数据是抽象类声明的对象,而不是具体类声明的对象.就是利用abstract来设计实现用户需求. 比如:我 ...