C# 关键字const和readonly的区别

const和readonly都是给字段设置常量。何谓常量,是指在程序中直接给出其值,在整个操作过程中其值保持不变的数据。

const关键字是静态常量,在编译时就初始化好,对于每一次编译后的结果,const的值是固定的,它指定的全局变量或局部变量的值不能被修改。

而readonly的值是可以在运行的时候才确定值的~~.

使用场景 

1、const定义常量后,是一个固定的硬编码值,不允许再次修改,而readonly允许在类的构造函数中进行再次赋值

2、在不同类实例中有不同的实例变量,实例变量可以采用readonly

Static Readonly

const 是编译时常量,readonly 是运行时常量,const 较高效,readonly更灵活,在应用上一般都以 static readonly 来代替const,以平衡const在灵活性上的不足,所以static readonly等效于const。

static readonly允许在类的静态构造函数中进行赋值

Const比ReadOnly效率高

因为const变量经过编译器编译后,我们在代码中引用const变量的地方会用const变量所对应的实际值来代替

const int value = 1000;Console.WriteLine(value);

和下面代码所生成代码的IL是一致的

Console.WriteLine(1000);

Readonly比Const灵活

字段声明为const,则它不是一个变量,而是一个笃定的硬编码值 ,它是隐式static的
readOnly允许把一个字段设置为常量,但也可以执行一些运算,以确定她的初始值。可以在构造函数中给readonly字段赋值,但不能在其它地方。它还可以是个实例变量而不static的,每个类都有不同的值 ,和const不同,要定义为static,必须显式的声明

class Program{  static readonly int readValue = 2000;  static Program()  {    readValue = 55; //只能在构造函数上下文中给它赋值  }  static void Main(string[] args)  {    Console.WriteLine(readValue);  }}

readonly变量是运行时变量,其赋值行为发生在运行时。readonly的全部意义在于,它在运行时第一次被赋值后将不可以改变。当然,“不可以改变”分为两层意思:
1)对于值类型变量,值本身不可改变(readonly,只读)。
2)对于引用类型变量,引用本身(相当于指针)不可改变。
首先我们来看值类型变量,如下代码:

public class Sample{public readonly int readValue;public Sample(int value)    {         readValue = value;    }}

Sample的实例readValue在构造方法中被赋值后就不可以改变,下面的代码将不会编译通过

Sample sample = new Sample(100);//sample.intValue = 18; //无法对只读的字段赋值(构造函数或变量初始值指定项中除外)Console.WriteLine(sample.readValue);

readonly所代表的运行时含义有一个重要的作用,就是可以为每个类的实例指定一个readonly的变量。以Sample这个类为例,可以在运行时生成多个实例,而同时,又可以为每个实例生成自己的readonly变量,如下:

Sample sample = new Sample(100);Sample sample = new Sample(200);Sample sample = new Sample(300);

针对引用类型变量,如下代码

public readonly Student student;public Sample(Student value){     student = value;}

Sample的ReadOnlyValue是一个引用类型变量,赋值后,变量不能再指向任何其他的Student实例,所以,下面的代码将不会编译通过:

Sample sample = new Sample(new Student() { Id = 1, name = "张小三" });//sample.student = new Student() { Id = 2, name = "张小四" }; //无法对只读的字段赋值(构造函数或变量初始值指定项中除外)Console.WriteLine(sample.student.name);

但是,我们之前已经提到过了,引用本身不可改变,引用所指的实例的值,却是可以改变的,下面的代码将会被允许:

Sample sample = new Sample(new Student() { Id = 1, name = "张小三" });sample.student.name = "张小四";Console.WriteLine(sample.student.name);

const和readonly区别:

C# 关键字const和readonly的区别

题外话:静态构造函数和普通构造函数哪个先执行?

class Sample{public Sample()     {          Console.WriteLine("普通构造函数");     }static Sample()     {          Console.WriteLine("静态构造函数");     }}输出打印结果:普通构造函数静态构造函数