ITPub博客

首页 > Linux操作系统 > Linux操作系统 > ViewState Session Static区别

ViewState Session Static区别

原创 Linux操作系统 作者:CodeAgriculture 时间:2013-03-26 15:11:27 0 删除 编辑
Normal 0 0 2 false false false EN-US ZH-TW X-NONE一、ViewState与Static的区别:
在做BS模式的页面时也用static变量,殊不知Asp.net中的static已不同于CS中的static。原因很简单,就是因为在Asp.net中所有的用户将使用同一个static变量。这就意味着每一个使用该页面的用户对该变量的操作将会影响到其他用户。就拿上面计数器的例子来说,假设times初试值为0,因为此时只有我们自己在使用这个页面,当然不会有什么问题,但如果有两个人同时连接到这个页面,如果A单击了Button1一次,则B刷新页面后Label1将显示1,如果B再单击Button1一次,则times变成2,两个人刷新页面后就出现问题了:A和B都会说,我明明只单击了Button1一次,怎么Label1就显示我单击了两次哪?——这就是因为两个人共享的是服务器上同一个times,任何一个人对times的操作都会在使用该页面的他人的浏览器中表现出来。问题就出在这里。
    怎么办哪?还好,除了传统的Asp中的Session对象外,Asp.net提供了一个更好的ViewState对象。ViewState对象用来保存页面中的各种变量,甚至是对象。使用方法和HashTable类似,只要用变量名称做索引,如ViewState["Var"],就可以用存取变量Var的值,而不管Var是普通变量,还是对象,甚至是内存中的一张DataTable,太方便了。为什么可以用ViewState而不能用static变量哪?原因就是服务器端会为每个连接到该页面的用户分别建立一个ViewState,所以ViewState相当于页面级的Session。这下我们可以放心地使用ViewState来存取需要暂存的变量和对象了。
    ViewState的用法很简单,如下所示:
    1、保存变量到ViewState中:
       ViewState["times"]=times;//存放普通变量times
       ViewState["Orders"]=dtOrders;//存放DataTable型对象dtOrders
    2、读出ViewState中的值:
       times=(int)ViewState["times"];
       dtOrders=(DataTable)ViewState["Orders"];
    看见了吧?就如此简单!有的朋友会问读出变量的值时为什么要进行强制类型转换?这是因为当变量(不管是int型的普通变量times,还是DataTable型的对象dtOrders)被存放到ViewState中后,ViewState可不管你是普通变量还是对象,统统按Object来对待。所以当我们取出存放在ViewState中的东西时,一定要转换成相应的类型,否则就会报错。而这一操作不用在用ViewState保存变量时进行,系统会自动转换。(注意ViewState括号中的字符串只是为了标识不同变量的索引,用不着非要和变量同名)所以上面计数器的代码应该这样写才好:
       ...
       ViewState["times"]=0;
       ...
       private void Button1_Click(object sender,EventArgs e)
       {
           int times=(int)ViewState["times"];
           times++;
           ViewState["times"]=times;
           Label1.Text=times.ToString();
        }
    一般情况向下,将要保存到ViewState中的对象(或变量)用属性的形式来实现会更方便。如对于上述的计数器times,可以这样处理:
    ...
    private int times
    {
        get
         {
            return (int)ViewState["times"];
         }
        set
        {
            ViewState["times"]=value;
        }
    }
    ...
    private void Button1_Click(object sender,EventArgs e)
     {
        times++;
        Label1.Text=times.ToString();
     }
    ...
    在这里times将当作私有属性来操作,是不是非常方便?
    那是不是说static型变量就没用了哪?当然不是!在C#中用static声明的类不用实例化直接使用。正是由于所有用户共享服务器端的同一个static变量,所以可以用static型对象来存取一些公用的处理模块,比如类型转换、变量验证等工作。所以要根据具体情况而定。
    还有一点需要注意:如果在页面中多个过程要共享一个对象或变量,我们在页面类的开始部分定义一个页面级的全局变量是不行的,static本来可以,但上面说了这种类型的变量不安全,所以这时就可以用ViewState。
 二、ViewState与Session的区别
session值是保存在服务器内存上,那么,可以肯定,大量的使用session将导致服务器负担加重. 而viewstate由于只是将数据存入到页面隐藏控件里,不再占用服务器资源,因此, 我们可以将一些需要服务器"记住"的变量和对象保存到viewstate里面. 而sesson则只应该应用在需要跨页面且与每个访问用户相关的变量和对象存储上. 另外,session在默认情况下20分钟就过期,而viewstate则永远不会过期.

但viewstate并不是能存储所有的.net类型数据,它仅仅支持String、Integer、Boolean、Array、ArrayList、Hashtable 以及自定义的一些类型.

当 然,任何事物都有两面性, 使用viewstate会增加页面html的输出量,占用更都的带宽,这一点是需要我们慎重考虑的. 另外, 由于所有的viewstate都是存储在一个隐藏域里面,用户可以很容易的通过查看源码来看到这个经过base64编码的值.然后再经过转换就可以获取你 存储其中的对象和变量值.

其实,对于viewstate的安全性问 题,asp.net还给我们提供了更多的选择.一般如果要保护viewstate有两种方式: 一种是防篡改,一种是加密. 一说到防篡改,我们就想起了使用散列代码. 没错, 我们可以在页面顶部加入如下代码:Page EnableViewStateMAC=true

这 样asp.net就会自动的在viewstate中追加一个散列码,在页面回传时,服务器根据回传的viewstate生成一个散列码,再与回传的散列码 相比较,如果不对,则丢弃该viewstate,同时控件将恢复初试状态. (默认情况下asp.net是通过SHA1算法而不是md5算法来生成散列,不过这个可以在machine.config里面配置machineKey validation="MD5"即可)

而viewstate加密就更简单了, 只要在machine.config里设置一下machineKey validation="3DES"即可实现用des加密viewstate了.

来自 “ ITPUB博客 ” ,链接:https://blog.itpub.net/28699126/viewspace-757171/ ,如需转载,请注明出处,否则将追究法律责任。

下一篇: 自定义分页控件
请登录后发表评论 登录
全部评论

注册时间:2013-03-07

  • 博文量
    54
  • 访问量
    435952