第六章类(十八)readonly与const
常量应是恒定不变,如果修改它,在使用它的程序集中不一定能反映出最新改变。
如一个程序集引用了另一个程序集中的常量,常量值将直接编译到引用程序集中。所以,如果被引用程序集中的值发生改变,而引用程序集没有重新编译,那么引用程序集将继续使用原始值而非新值。
将来可能改变的值应指定为readonly。
readonly英文译义是只读的,同样它也是字段的修饰符。
这是之前上篇的例子,正如您可以看到的IL代码的const字段numberOfdays的值(7)直接嵌入IL代码。
其中,readonly字段piValue显示为piValue。该值可在运行时获得。
然后一开始描述的那段文字,用代码解释。
类(A)
public class ReadonlyConstant { public const int numberOfDays = 7; //字段 public readonly double PI=3.14; //内联初始化 public readonly int znumber; public readonly List<int> readonlyList; public ReadonlyConstant() { znumber= 50;//构造函数初始化 } public ReadonlyConstant(int x) { znumber=100; } public NormalMethod() { //readonly int i=0; 这是错误的 } }
类库A在另一个项目(B)中使用它作为参考。现在看一下生成的项目B的IL代码
在项目B的代码中,在IL代码中嵌入的常量字段数的值。现在的问题是,在源中(A类库的ReadonlyConstant.cs),常量字段 (numberOfdays )值改为5,并编译并生成一个新的dll。
但是,除非我们编译这个项目,否则这个常量字段的新值不会影响B项目。编译后,新的常量字段值将嵌入到项目B的IL代码中。
在C#中何时使用常量和readonly
当值是绝对不变的时候,使用常量,这在时间上是不变的。例如一周的天数是7。这始终是常数。
由于在IL内嵌有不变的值,我们可以使用常量修饰符来获得性能上的好处。
如果我们想要对类(或对象)的不同实例使用不同的常量值,请使用readonly。