如果我已将此类定义为ASP.NET 2.0中应用程序的一部分:
public class Foo
{
private static int _seed = 100;
private static object myLock = new object();
public Foo()
{
lock (myLock)
{
this.MyInt = _seed;
_seed++;
}
}
public int MyInt {get; set;}
}
(编辑:更新以解决答案所指出的线程安全问题)
该静态成员的行为如何?它会从100开始并为每个会话单独递增,还是会在每次刷新时单独递增,还是全局...?
注意:我问这个是因为我在ASP.NET应用程序中第一次使用类来建模数据,而且我已经发现ViewView序列化似乎忽略了C#的by-reference性质,所以我想知道我可以期待的其他奇怪之处。例如,如果我定义了这个类(假设Bar
是另一个类):
public class OtherFoo
{
public List<Bar> Bars {get; set;}
}
我在我的页面上这样做:
OtherFoo _myFoo = new OtherFoo();
//Code here to instantiate the list member and add some instances of Bar
Bar b = _myFoo.Bars[0];
ViewState["myFoo"] = _myFoo; //Assume both are [Serializable]
ViewState["myBar"] = b;
当我在下一次回发中将这些内容从ViewState中删除时,b
和_myFoo.Bars[0]
不再是同一个对象。
答案 0 :(得分:3)
ASP.NET并不神奇。它并没有神奇地将C#编程语言(或任何其他语言)转换为了解Web开发(会话,请求等)的语言。
您的代码将完全 ,就像在任何其他类型的应用程序中一样,并且可以同时由多个线程调用它(因此使用“++”不是安全)。
同样,没有魔力。与其他所有应用程序一样,静态的生命周期仅限于AppDomain的生命周期,其中包含静态类型的类型。
ASP.NET应用程序中的AppDomain是在第一次访问应用程序时创建的(除非IIS设置强制它预先启动),并且仅在特定时间结束,例如{{1}中的程序集时}文件夹已更改,或者bin
已更改,或者IIS设置表明AppPool需要回收。
答案 1 :(得分:1)
每次调用构造函数时都会增加种子。请注意,这可能发生在多个线程中,因此您最好使其线程安全。
反序列化将导致调用(默认)构造函数。如果将它序列化为ViewState,则ASP.NET将在回发时反序列化对象,从而调用构造函数。
请注意,C#语言和asp.net框架在另一个层面上。该框架(主要)用C#编写,它将在幕后为您做很多事情,但它仍然遵循语言规则和运行时。
序列化只不过是将对象(或对象图)的信息编码为流。如果对其进行反序列化,则会返回相同的信息,但它与您开始使用的对象不同。同样,这不是魔术,您可以使用属性和反射编写自己的序列化库。