返回首页


{S0}简介
ASP.NET ViewState是一个伟大的机制,简化的ASP.NET开发人员的生活。但是,大家都知道,在。NET Framework节省您的ASPX页面上作为隐藏字段的ViewState数据。如果您的网页只有少数控制,这是没有问题的。但是,如果你的页面有一些面板和/或一些DataGrid中,在这篇文章中表现出的技术,,你可以大大减少页面加载时间。
我们将开始我们的分析思维框架需要的地方工作的ViewState隐藏字段保存的数据。答案是:只有在服务器端。该系统并不需要工作在客户端的ViewState数据,因此,如果我们开始这一数据再次保存,而不是从服务器到客户端在进行这一切,从客户机到服务器的服务器,我们而载入我们的文件,将节省大量的时间。你可能不会注意的差异,而同一台计算机上安装该应用程序加载的页面,但是,使用拨号连接来测试它,你会看到发生什么事。你冷也看到了与没有这种技术生成的源代码的大小。
这个例子包含一个类继承的System.Web.UI.Page,并覆盖方法SavePageStateToPersistenceMedium和LoadPageStateFromPersistenceMedium。这些方法负责保存和加载页面上的控件使用ViewState的。我们做的是拦截调用这些方法,使用Web.config中一些简单的自定义配置项,设置这个类应该是如何工作的。它可以使用两个目的地的服务器上保存的ViewState:会话和缓存,并有工作能力的原始类,节能的ASPX页面的ViewState数据。
如果你已经有一个项目要开始使用这种技术,所有你需要做的是添加一个引用,伴随着这个例子的类和继承您的"代码隐藏文件",而不是系统。 Web.UI.Page,并添加到Web.config配置信息。
为了开发这种技术,我读了很多在互联网上的文章,但是,一个真正的"打开我的心"如何做这个实现可以和它的好处。见利益节点数的详细信息。
我包括一个演示项目,你可以下载和使用测试执行。需要注意的是示范项目的会议上,我认为这是最好的地方来存储它的ViewState保存。使用代码
正如我所说的,实施是很容易的。所以,让我们开始与我的类的代码,并讨论后,让我们看到的Web.config文件的配置。"ASPX页面的ViewState"作者:Rgis丹尼尔德奥利韦拉。"电子邮箱:regisxp@hotmail.com"日期..:07/2005"Reserach来源:"http://www.eggheadcafe.com/articles/20040613.asp进口System.Configuration.ConfigurationSettings进口System.Diagnostics公共类VSPage 继承的System.Web.UI.Page
现在,让我们来看看负责保存ViewState数据,称为SavePageStateToPersistenceMedium的方法。 ,这种方法是,如果我们的web.config文件ServerSideViewState是启用(true)。如果没有,系统将执行一个正常的ViewState保存,其存储的ASPX文件。如果有的话,系统会检查这是ServerSideViewState方法要使用高速缓存或会话。如果您选择的CACHE,将数据存储在缓存,并将于一段时间后,。如果您选择会话,数据将被保存在用户会话和用户会话到期时,将被丢弃。使用此选项时,系统会自动创建一个DataTable的会议上,将保留所有的ViewState数据将被保存。 ViewState数据,可在DataTable中举行的最大数量是指在Web.Config参数ViewStateTableSize。默认值为150,代表,过去的150回传的ViewState数据将提供给系统。因此,如果用户点击导航器的后退按钮的150倍(什么是不可能发生的),该页面的ViewState将已经存在要使用。这是一个很好的的数字... ...受保护的覆盖子_  0;SavePageStateToPersistenceMedium(#对象的ViewState)  0; 作为字符串昏暗的VSKey '字符串,将举行的唯一键 "用于引用这个ViewState数据 Debug.WriteLine(MyBase.Session.SessionID) "创建基础上的SessionID的关键,对Request.RawUrl &# 160; "和上的确切时间representated蜱 "而被保存在页面 VSKey ="VIEWSTATE_quot;放大器,MyBase.Session.SessionID放大器;"_quot;放大器; - Request.RawUrl放大器;"_quot;放大器; Date.Now.Ticks.ToString &# 160; "检查,如果ServerSideViewState被激活&# 160; 如果UCASE(的AppSettings("ServerSideViewStatequot;))="; TRUEquot",然后 "检查,我们将保存ViewState数据  60; 如果UCASE(的AppSettings("ViewStateStorequot;))="; CACHEquot",然后  60; "存储在缓存中的ViewState &# 160; Cache.Add(VSKey,ViewState的,没什么,_ Date.Now.AddMinutes(Session.Timeout),_ & #160; Cache.NoSlidingExpiration,  0; Web.Caching.CacheItemPriority.Default,没什么) "ViewStateData本届会议将被保存  0; 其他 由于DataTable中的DIM VsDataTable  60; 作为DataRow的DIM DbRow & #160; "检查的ViewState的DataTable会议 如果然后IsNothing(会议("; __VSDataTablequot";))  60; "不,不是这样的。创建它... DIM PkColumn(1),DbColumn的DataColumn  0; VsDataTable =新的DataTable("VStatequot;)  0; '创建的DataTable   ; "列1 - 名称:VSKey - 的PrimaryKey DbColumn =新的DataColumn("; VSKeyquot";的GetType(字符串)) &# 160; VsDataTable.Columns.Add(DbColumn)  0; PkColumn(0)= DbColumn  0; VsDataTable.PrimaryKey = PkColumn  60;"列2 - 名称:ViewStateData  0; DbColumn =新的DataColumn("VSDataquot;对象的GetType())  0; VsDataTable.Columns.Add(DbColumn) "列3 - 名称:日期时间 DbColumn =新的DataColumn("DateTimequot;,的GetType(日期)) &# 160;VsDataTable.Columns.Add(DbColumn)  0; 其他   ; "ViewState的数据表已经上UserSession   ;会议VsDataTable =("__VSDataTablequot;) 结束如果 &# 160; "检查,如果我们已经使用相同的密钥保存的ViewState。  60;"如果有的话,更新,而不是创建一个新行。  60; "(这是非常dificult发生)&# 160; VsDataTable.Rows.Find DbRow =(VSKey)   ; 如果不IsNothing(DbRow)  0; "行!!创建一个新的更新,而不是... &# 160;DbRow("VsDataquot;)= ViewState中 & #160; 其他 &# 160; "创建一个新行... DbRow = VsDataTable.NewRow  ; DbRow("VSKeyquot;)= VSKey   ; DbRow("VsDataquot;)= ViewState中  0; DbRow("DateTimequot;)= Date.Now  0; VsDataTable.Rows.Add(DbRow)   ; 结束如果 & #160; "检查,如果我们的DataTable是超大...  60; 如果Convert.ToInt16(的AppSettings("; ViewStateTableSizequot";))_ & #160; 然后LT; VsDataTable.Rows.Count 0; Debug.WriteLine("删除的ViewState在quot; - &# 160; 放大器; DbRow(2)放大器",编号quot;放大器; DbRow(0))  60; VsDataTable.Rows(0),删除()'删除第一行。 & #160; 结束如果  60; "存储在会话的DataTable。 & #160; 会议("__VSDataTablequot;)= VsDataTable 结束如果  0; "注册页面上的一个HiddenField, &# 160; "包含UniqueKey产生。 &# 160;"有了这个,我们将能够找到的ViewState &# 160; "从这个网页,通过检索这些值。  60; RegisterHiddenField("; __VIEWSTATE_KEYquot";,VSKey) 其他 "通话的正常进程。 MyBase.SavePageStateToPersistenceMedium(视图状态) 结束如果 END SUB
现在,让我们来看看负责的方法来加载ViewStateData,LoadPageStateFromPersistenceMedium:保护覆盖功能LoadPageStateFromPersistenceMedium()作为对象 & #160; "Verifica SE Ø ServerSideViewState EST??ativado 如果UCASE(的AppSettings("ServerSideViewStatequot;))="; TRUEquot",然后  60; DIM VSKey作为字符串'的ViewState UniqueKey & #160; VSKey =的Request.Form("__VIEWSTATE_KEYquot;) "请求页面的重点和validade。  0; 如果没有VSKey.StartsWith("VIEWSTATE_quot;) &# 160; 抛出新的异常("无效VIEWSTATE重点:"放大器; VSKey)  60; 结束如果   ; "验证现在,这是我们需要对我们的配置文件web.config:LT插入; - 应用程序特定的设置 - >! LT; appSettingsgt; LT; - ServerSideViewState:定义如果的ViewState 将被保存在服务器上:真| FALSE - GT; LT;添加键="ServerSideViewStatequot;值= quot; Truequot; / GT; !LT - ViewStateStore:定义,我们将保存在ViewState:缓存|会议 - GT; LT;添加键="ViewStateStorequot;值= quot; Sessionquo​​t; / GT; LT; - ViewStateCacheFSSize:定义的最大数量 & #160; viewStates将被保存时ViewStateStore =会议 - GT; 60; LT;添加键="ViewStateTableSizequot;值= quot; 150quot; / GT; LT; / appSettingsgt;兴趣点
大量的研究是为了实现本文提出的登录。最有趣的来源之一。如果您想了解有关这些技术的更多信息,看到一些压力测试的结果,按照链接。结论
ViewState的真正简化的ASP.NET应用程序的发展,但由于在页面加载时间增加,一些开发商不喜欢使用它。利用这种技术,你可以使用在您的项目没有对生成的页面源代码的大小担心的ViewState的所有优势。

回答

评论会员:游客 时间:2011/12/05
会员4128618:好一个
k666
评论会员:游客 时间:2011/12/05
我实现了我的应用程序类似的东西。我觉得现在的是,当用户按刷新(F5)LoadPageStateFromPersistenceMedium不叫。埃尔戈没有视图状态是恢复和崩溃。解决这一问题的任何想法?肯
会员781610
评论会员:游客 时间:2011/12/05
您好,我是一个新手DOTNET编程。会不会保持在会议的ViewState信息,降低服务器的性能。万岁
没有人知道的一切
评论会员:游客 时间:2011/12/05
我只是WANA谢谢..一个绝妙的主意,可能影响页面的大小。更安全...imgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_53_1.gifimgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_53_2.gif
奥利弗在新西兰
评论会员:游客 时间:2011/12/05
imgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_53_3.gif嗨,只是想知道这种技术是否会导致存储在服务器的内存视图状态的瓶颈到Web服务器时,例如有有数以千计的网站上的访问者同时?
asomalra
评论会员:游客 时间:2011/12/05
Thany,能否请您发表您的简化代码,因为正如你所说,太多的回传中添加多个记录到DataTable中。我很欣赏
thany
评论会员:游客 时间:2011/12/05
这是真的不坏。一个外箱思维一次imgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_53_1.gif很好的例子然而,使用一个DataTable,并存储到会话中没有这样一个好主意。每次回发时,又增加了本表中的记录(但最多不得超过)。该viewstates不删除这种方式。你真的从来没有需要存储超过当前视图状态,所以一个表来存储它们是多余的。我创建了一个简单的类保存的网址,SESSIONID和ViewState和我店,直接进入了会议,使用恒定的关键。此外,这个想法是伟大的imgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_53_1.gif
mercede
评论会员:游客 时间:2011/12/05
当使用您的解决方案,该项目是利用部分回传时,败得很惨。我认为它可能是由于以下原因。每SaveToPersistentMedium()调用,生成一个新的关键是对视图状态。其余的页面上的控件已经使用以前项,我试图修复它,但不能。主要问题是崩溃,是一个完整的回传时bcoz,ViewState数据stoed变得无效。任何解决方案?
asomalra
评论会员:游客 时间:2011/12/05
使用AJAX时,任何解决方法的解决方案??
markrodrigues
评论会员:游客 时间:2011/12/05
嗯,我使用这种方法(略作修改)与AJAX更新的面板并没有得到任何问题,除非我尝试乱用后退按钮在这种情况下,,过多的AJAX去有点坚果反正周围因此,我建议尝试和看到,如果你有自己的问题。马克
aggrobot
评论会员:游客 时间:2011/12/05
如果您使用的AJAX调用注册的ClientScript,而不是使用隐藏字段的ScriptManager。所以:ScriptManager.RegisterHiddenField(这一点,VIEWSTATEFIELD,viewState.ToString());{BR}而不是:ClientScript.RegisterHiddenField(VIEWSTATEFIELD,viewState.ToString());{BR}它也适用于非AJAX页面太刚,只要你参考System.Web.Extensions.dll,所以没有必要为AJAX和传统的同步回发之间雪亮的处理程序代码。此外,你应该看看这个视频,如果你仍然有麻烦AJAX和浏览器的历史。imgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_39_0.gif
CassePer
评论会员:游客 时间:2011/12/05
喜当我们的一些用户已记录一段时间,他们得到一个错误时,VsDataTable是(中LoadPageStateFromPersistenceMedium):VsDataTable=会议("__VSDataTable")它似乎像会话已被清除/删除。我曾尝试增加超时,我们没有运气。1)LT;sessionStategt;在web.config超时设置为70分钟2)该站点在IIS6中的会话超时设置为70分钟3)在应用程序池的工作进程空闲超​​时设置为70分钟ViewStateTableSize设置为300任何其他建议?imgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_53_6.gif{七}imgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_53_8.gif{七}imgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_53_8.gif{七}imgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_53_8.gif-8:12(星期三)9月27日,2006年修改{中六}
mindflower
评论会员:游客 时间:2011/12/05
张贴您的解决方案的感谢!,它可以优化的一点是,它保留了很多不必要的数据在会话。ViewState数据IST只需要最后的回传,可以删除后,它的用法。这些数据可以堆积起来,成为一个真正的问题在高流量的网站上。这里是我的建议更紧凑,更好地执行代码。它的工作原理罚款,除非一个框架使用不同的帧在同一时间(这是相当罕见),同一页上。当应用测试中心测试,该代码执行30%的有关RPM和内存。斯特凡公共抽象类ViewStatePage的System.Web.UI.Page{私人BOOL_bViewStateCacheEnabled=TRUE;受保护的虚拟BOOLViewStateCacheEnabled{{返回_bViewStateCacheEnabled;}集合{_bViewStateCacheEnabled=值;}}保护覆盖无效SavePageStateToPersistenceMedium(对象的ViewState){如果(this.ViewStateCacheEnabledConfigurationSettings.AppSettings["ServerSideViewState"]=NULLbool.Parse(ConfigurationSettings.AppSettings["ServerSideViewState"])){BR}{字符串sViewStateKey="__viewStateCache_"Request.FilePath;会议[sViewStateKey]=ViewState的;}ELSE{base.SavePageStateToPersistenceMedium(视图状态);}}保护对象覆盖LoadPageStateFromPersistenceMedium(){如果(this.ViewStateCacheEnabledConfigurationSettings.AppSettings["ServerSideViewState"]=NULLbool.Parse(ConfigurationSettings.AppSettings["ServerSideViewState"])){BR}{字符串sViewStateKey="__viewStateCache_"Request.FilePath;对象viewStateCache=会议[sViewStateKey](viewStateCache==NULL){Logging.Logger.Error("ViewStateKey未找到");返回null;}ELSESession.Remove(sViewStateKey);返回viewStateCache;}ELSE{返回base.LoadPageStateFromPersistenceMedium()}}}
markrodrigues
评论会员:游客 时间:2011/12/05
感谢您的细化mindflower我简化多一点。保护覆盖小组SavePageStateToPersistenceMedium(BYVAL作为对象的ViewState) "SaveViewstateInSession是一个新的属性页面如果(SaveViewstateInSession) DIMsViewStateKey作为字符串="VIEWSTATE_"Request.RawUrl会议(sViewStateKey)=ViewState的 ClientScript.RegisterHiddenField("__VIEWSTATE_KEY",sViewStateKey) ELSE MyBase.SavePageStateToPersistenceMedium(视图状态)最终如果ENDSUB 受保护的覆盖功能LoadPageStateFromPersistenceMedium()作为对象DIMsViewStateKey作为字符串的Request.Form("__VIEWSTATE_KEY"){B​​R}如果(String.IsNullOrEmpty(sViewStateKey)) 返回MyBase.LoadPageStateFromPersistenceMedium()最终如果返回会议(sViewStateKey)结束函数我可以打开此功能,只需通过设置在任何派生的页面构造新的基类的属性SaveViewstateInSession为true。每页如果我想我可以打开整个网站这一关有一个Web.config设置,但我不需要,这种方法并不担心是否SaveViewstateInSession或在LoadPageStateFromPersistenceMediumisturned;如果有一个__VIEWSTATE_KEY隐藏字段,它是尝试和检索本届会议,如果__VIEWSTATE_KEY没有设置,那么它只会默认为基类的行为。希望这是有用的,有人imgsrc=http://www.orcode.com/upimg/2011_12_05_09_15_53_1.gif马克
JeroenMX
评论会员:游客 时间:2011/12/05
。我觉得你错过了该点的地方他原来的关键是真正独特的(因此蜱页的rawurl),使得它有可能为用户来打开相同的页面不止一次{BR}
ameya gholap
评论会员:游客 时间:2011/12/05
理想的情况下,这应该是工作,我相信,如果SavePageStateToPersistenceMedium我什么也不做,不保存任何视图状态和在LoadPageStateFromPersistenceMedium我返回null,我仍然保持视图状态(只是罚款如初)看到的WebForms。只是它没有看到在webform。Theoritically这些方法似乎斜面被用来镇压/覆盖视图状态保存(只,其没有更多的形式)。我真的需要,并为这一个回答。提前感谢!
kiran1331
评论会员:游客 时间:2011/12/05
Ameya,要回答你的问题,如果你不重写LoadPageStateFromPersistenceMedium和SavePageStateToPersistenceMedium方法,然后基数法的实施将默认设置ViewState中,由于你能看到你正确的对象,设置它的状态。尝试从这些方法返回NULL,你会看到它创造什么含义。梅塔Harshdeep"一切皆有可能,只是取决于你如何玩游戏。"
MaynardK
评论会员:游客 时间:2011/12/05
我们等效的C#代码
deb1234
评论会员:游客 时间:2011/12/05
http://www.developerfusion.co。英国/公用事业/convertvbtocsharp.aspx
deb1234
评论会员:游客 时间:2011/12/05
其他人多嘴所有他们希望,它是在会话中存储的ViewState错误,但我可以看到有使用此当ViewState是必要的优势,你想,以减少文件大小发送到客户端的浏览器。无论如何,大文章。我可能会发现一两页,我想实现这个。Edbert体育澳大利亚悉尼