两种常量类型-readonly和const

C#中有两种常量类型,分别为readonly(运行时常量)与const(编译时常量),本文将就这两种类型的不同特性进行比较并说明各自的适用场景。
工作原理
readonly为运行时常量,程序运行时进行赋值,赋值完成后便无法更改,因此也有人称其为只读变量。
const为编译时常量,程序编译时将对常量值进行解析,并将所有常量引用替换为相应值。
下面声明两个常量:

public static readonly int A = 2; //A为运行时常量
public const int B = 3; //B为编译时常量
下面的表达式:

int C = A + B;
经过编译后与下面的形式等价:

int C = A + 3;
可以看到,其中的const常量B被替换成字面量3,而readonly常量A则保持引用方式。
声明及初始化
readonly常量只能声明为类字段,支持实例类型或静态类型,可以在声明的同时初始化或者在构造函数中进行初始化,初始化完成后便无法更改。
const常量除了可以声明为类字段之外,还可以声明为方法中的局部常量,默认为静态类型(无需用static修饰,否则将导致编译错误),但必须在声明的同时完成初始化。

数据类型支持
由于const常量在编译时将被替换为字面量,使得其取值类型受到了一定限制。const常量只能被赋予数字(整数、浮点数)、字符串以及枚举类型。下面的代码无法通过编译:

public const DateTime D = DateTime.MinValue;
改成readonly就可以正常编译:

public readonly DateTime D = DateTime.MinValue;
可维护性
readonly以引用方式进行工作,某个常量更新后,所有引用该常量的地方均能得到更新后的值。
const的情况要稍稍复杂些,特别是跨程序集调用:

public class Class1
{
public static readonly int A = 2; //A为运行时常量
public const int B = 3; //B为编译时常量
}

public class Class2
{
public static int C = Class1.A + Class1.B; //变量C的值为A、B之和
}

Console.WriteLine(Class2.C); //输出"5"
假设Class1与Class2位于两个不同的程序集,现在更改Class1中的常量值:

public class Class1
{
public static readonly int A = 4; //A为运行时常量
public const int B = 5; //B为编译时常量
}
编译Class1并部署(注意:这时并没有重新编译Class2),再次查看变量C的值:

Console.WriteLine(Class2.C); //输出"7"
结果可能有点出乎意料,让我们来仔细观察变量C的赋值表达式:

public static int C = Class1.A + Class1.B;
编译后与下面的形式等价:

public static int C = Class1.A + 3;
因此不管常量B的值如何变,对最终结果都不会产生影响。虽说重新编译Class2即可解决这个问题,但至少让我们看到了const可能带来的维护问题。

性能比较
const直接以字面量形式参与运算,性能要略高于readonly,但对于一般应用而言,这种性能上的差别可以说是微乎其微。

适用场景
在下面两种情况下:
a.取值永久不变(比如圆周率、一天包含的小时数、地球的半径等)
b.对程序性能要求非常苛刻
可以使用const常量,除此之外的其他情况都应该优先采用readonly常量。

时间: 2024-10-08 09:11:14

两种常量类型-readonly和const的相关文章

socket编程之二:两种链接类型upd和upd

前面一篇文章说到了一些计算机网络的基础知识,引入了socket,从这节开始,就进入正题了. 一 概率 TCP:Transimission Control Protocol传输控制协议. UPD:User Datagram Protocol用户数据包协议. 两者都属于上一篇文章说的OSI模型中的第四层--传输层的协议. 两者相比: TCP协议面向连接,UDP协议面向非连接:(链接) TCP协议传输速度慢,UDP协议传输速度快:(速度) TCP有丢包重传机制,UDP没有:(重传) TCP协议保证数据

java List递归排序,无序的列表按照父级关系进行排序(两种排序类型)

当有一个List列表是无序的,List中的数据有parentid进行关联,通过java排序成两种排序类型: 所用的测试列表最顶级无parentid,若为特殊值,修改下判断方法即可. 第一种排序:按照树结构进行排序 排序前:122,13,121,1,131,12,132...无序的[TestSort [id=122, name=三级b, parentid=12], TestSort [id=13, name=二级b, parentid=1], TestSort [id=121, name=三级a,

【SSH进阶之路】Spring的IOC逐层深入——依赖注入的两种实现类型(四)

上篇博文,我们介绍了为什么使用IOC容器,和IOC的设计思想以及IOC容器的优缺点,并且给大家转载了一篇介绍IOC原理的博文,我们这篇主要给大家依赖注入的两种方式,以及他们的优缺点. 我们这篇博文还是使用上篇博客中添加用户的实力,只是给大家在注入对象的方式上发生一点点变化,为了让大家更加容易接受.下面我们开始: 构造器注入 构造器注入,即通过构造函数完成依赖关系的设定.我们看一下spring的配置文件: <?xml version="1.0" encoding="UTF

Kubernetes中,两种常见类型的Volume深度实践

一.背景 存储资源在所有计算资源中扮演着十分重要的角色,大部分业务场景下都有可能使用到各类存储资源.在Kubernetes中,系统通过Volume对集群中的容器动态或静态提供存储资源.通常情况下,我们可以认为容器或者Pod的生命周期时短暂的,当容器被销毁时,容器内部的数据也同时被清除.为了持久化保存容器的数据,Kubernetes引入了Volume,类似于Docker的Volume(Docker also has a concept of volumes, though it is somewh

变量的两种不同类型

变量可能包含两种不同数据类型的值:基本类型值和引用类型值. 基本类型值指的是简单的数据段,而引用类型值指那些可能由多个值构成的对象. 在将一个值赋给变量时,解析器必须确定这个值是基本类型值还是引用类型值. 5 种基本数据类型: Undefined . Null . Boolean . Number 和 String .这 5 种基本数据类型是按值访问的,因为可以操作保存在变量中的实际的值. 引用类型的值是保存在内存中的对象.与其他语言不同,JavaScript 不允许直接访问内存中的位置,也就是

《自拍教程》两种文件类型

计算机只认识0,1,所以计算机的世界, 所有的文件数据都应该是0,1组成的. 但是为了方便人类能阅读及理解, 逐步有了ASCII,UTF-8, GBK, GB2312等编码格式. 以上如果测试同学听晕乎,记住以下两种计算机文件的类型即可. 纯文本文件 人类可以识别的文字文本文件, 其文件以纯文本形式存储数据(数字和字母包括ASCII码和其他各国语言文字). 纯文本意味着该文件是一个字符序列,不含必须像二进制数字那样被解读的数据, 以Windows操作系统为例,包括: table.datafram

opengl两种投影类型

openGL两种投影方式 from http://hi.baidu.com/fcqian/blog/item/cc5794ec76807a3f27979131.html 投影变换是一种很关键的图形变换,OpenGL中只提供了两种投影方式,一种是正射投影,另一种是透视投影.不管是调用哪种投影函数,为了避免不必要的变换,其前面必须加上以下两句: glMAtrixMode(GL_PROJECTION); glLoadIdentity(); 事实上,投影变换的目的就是定义一个视景体,使得视景体外多余的部

php变量中两种特殊类型

第一种----资源 资源(resource):资源是由专门的函数来建立和使用的,例如打开文件.数据连接.图形画布.我们可以对资源进行操作(创建.使用和释放).任何资源,在不需要的时候应该被及时释放.如果我们忘记了释放资源,系统自动启用垃圾回收机制,在页面执行完毕后回收资源,以避免内存被消耗殆尽. <?php //首先采用"fopen"函数打开文件,得到返回值的就是资源类型. $file_handle = fopen("/data/webroot/resource/php

ajax 另外两种返回类型(json xml)

返回json类型(例子): <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv=