当前位置:编程学习 > C#/ASP.NET >>

ViewState的一些疑问

小弟不才,属于初学者,在进行项目练习时,遇到ViewState问题,需要使用repeater控件进行绑定后台数据,在页面上显示,这就造成了页面上的ViewState字段的长度进行大量增长,造成了页面加载速度的降低,本人对ViewState的了解仅涉猎于表面理解,知道它是记录一些值,帮主页面记忆一些值,通过对它的解码,发现全是后台绑定的数据,我的目前疑问是,是把整个页面的ViewState禁用还是禁用数据控件的? --------------------编程问答-------------------- 看情况,一种是启用viewstate,会增加页面的代码;另一种是禁用Repeater的viewstate,但需要每次请求页面时都执行查询数据库并绑定Repeater,可以专门写个方法。如果页面上没有会发生“回发”的按钮、超链接等,可以禁用页面级的viewstate、否则只禁用控件级的即可。 --------------------编程问答--------------------
引用 1 楼 dalmeeme 的回复:
看情况,一种是启用viewstate,会增加页面的代码;另一种是禁用Repeater的viewstate,但需要每次请求页面时都执行查询数据库并绑定Repeater,可以专门写个方法。如果页面上没有会发生“回发”的按钮、超链接等,可以禁用页面级的viewstate、否则只禁用控件级的即可。

+1 --------------------编程问答-------------------- 你的网络下载速度是多少?__ViewState多出来的字节占用了多少下载速度?

如果确实很大,以至于页面提交时会出现解析错误,那么可以使用这个类替换为你的Page的父类:
using System;
using System.IO;
using System.Linq;
using System.Runtime.Serialization.Formatters.Binary;
using System.Threading;
using System.Web.UI;

public class VPage : Page
{
    static private DirectoryInfo _Dir;

    private static DirectoryInfo Dir
    {
        get
        {
            if (_Dir == null)
            {
                _Dir = new DirectoryInfo(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "App_Data"));
                if (!_Dir.Exists)
                    _Dir.Create();
                _Dir = new DirectoryInfo(Path.Combine(_Dir.FullName, "ViewState"));
                if (!_Dir.Exists)
                    _Dir.Create();
            }
            return _Dir;
        }
    }

    protected override object LoadPageStateFromPersistenceMedium()
    {
        PageStatePersister ps = this.PageStatePersister;
        ps.Load();
        if (ps.ControlState != null)
            ps.ControlState = 反序列化对象((string)ps.ControlState);
        if (ps.ViewState != null)
            ps.ViewState = 反序列化对象((string)ps.ViewState);
        return new Pair(ps.ControlState, ps.ViewState);
    }

    protected override void SavePageStateToPersistenceMedium(object state)
    {
        PageStatePersister ps = this.PageStatePersister;
        if (state is Pair)
        {
            ps.ControlState = ((Pair)state).First;
            ps.ViewState = ((Pair)state).Second;
        }
        else
            ps.ViewState = state;
        if (ps.ControlState != null)
            ps.ControlState = 序列化对象(ps.ControlState);
        if (ps.ViewState != null)
            ps.ViewState = 序列化对象(ps.ViewState);
        ps.Save();
    }

    private object 反序列化对象(string stateID)
    {
        if (stateID == null)
            return null;

        object state = Cache[stateID];
        if (state == null)
            using (var stream = File.OpenRead(Path.Combine(Dir.FullName, stateID)))
                state = new BinaryFormatter().Deserialize(stream);
        else
            Cache.Remove(stateID);
        return state;
    }

    private string 序列化对象(object obj)
    {
        string stateID = Guid.NewGuid().ToString("N");
        Cache.Insert(stateID, obj, null, DateTime.Now.AddMinutes(5), System.Web.Caching.Cache.NoSlidingExpiration);
        using (var stream = File.Create(Path.Combine(Dir.FullName, stateID)))
            new BinaryFormatter().Serialize(stream, obj);
        return stateID;
    }

    static VPage()
    {
        ThreadPool.QueueUserWorkItem(h =>
        {
            var et = DateTime.Now.AddMinutes(-30);
            Dir.GetFiles()
                .Where(f => f.LastAccessTime < et)
                .ToList()
                .ForEach(f =>
                {
                    try
                    {
                        f.Delete();
                    }
                    catch { }
                });
        });
    }
}
它是使用本地的缓存和硬盘,来取代远程客户端。 --------------------编程问答-------------------- 其实很多人对于asp.net的应用并没有分别看清。假设你想模仿各大网站的那种去写网页,那么你的页面根本不应该有任何回发设计,凡是需要用户体验好一点的信息提交应该使用ajax,凡是根本不用顾用户体验的信息提交全都像asp那样通过<form />提交到另外一个页面(刷新整个页面)。

但是要注意,这可不是在开发企业应用程序。

对于企业应用程序,传统的asp.net的那种仿 winform 的状态机制,过去曾经是非常适合的。但是这几年已经完全跟不上 ajax 的潮流了。除非你使用silverlight这类比较高级的平台,使用jquery或者asp要想做出一个用户体验比较好的、有着非常丰富的界面布局和很多内容的“大”画面的web应用,是非常困难的。这样的页面根本不用在页面跳来跳去,而是无刷新地让用户“沉浸”在一个页面上一段时间就能干完持续一个小时以上的业务操作。 --------------------编程问答-------------------- 学习 --------------------编程问答-------------------- 首先感谢以上回复的朋友,AJAX目前还没有学习到,项目实战结束了才会进行学习,所以就要在不实用AJAX的情况下进行设计了,因为页面上有些新闻和产品都需要到数据库进行读取连接和内容,有专门的SQLHelper类,使用的是存储过程,目前的小疑问得到了解决,但是又有了点新的需求,怎么更好的去理解VIEWSTATE和更好的利用它去干一些漂亮的事情, --------------------编程问答-------------------- 学习了…………
补充:.NET技术 ,  ASP.NET
CopyRight © 2012 站长网 编程知识问答 www.zzzyk.com All Rights Reserved
部份技术文章来自网络,