常量
const 用于表示在程序的整个生命周期中永远不会改变的值。它的值在编译时是常量,而不是 readonly 关键字,其值在运行时是常量。
例如,由于光速永远不会改变,我们可以将它存储在一个常数中。
const double c = 299792458; // Speed of light
double CalculateEnergy(double mass)
{
return mass * c * c;
}
这与 return mass * 299792458 * 299792458 基本相同,因为编译器将直接用其常量值替换 c。
因此,c 一旦声明就无法更改。以下将产生编译时错误:
const double c = 299792458; // Speed of light
c = 500; //compile-time error
常量可以使用与方法相同的访问修饰符作为前缀:
private const double c = 299792458;
public const double c = 299792458;
internal const double c = 299792458;
const 成员本质上是 static。但是,不允许明确使用 static。
你还可以定义方法本地常量:
double CalculateEnergy(double mass)
{
const c = 299792458;
return mass * c * c;
}
这些不能以 private 或 public 关键字作为前缀,因为它们隐含在它们定义的方法的本地。
并非所有类型都可以在 const 声明中使用。允许的值类型是预定义类型 sbyte,byte,short,ushort,int,uint,long,ulong,char,float,double,decimal,bool 和所有 enum 类型。尝试使用其他值类型(例如 TimeSpan 或 Guid)声明 const 成员将在编译时失败。
对于特殊的预定义引用类型 string,可以使用任何值声明常量。对于所有其他引用类型,可以声明常量,但必须始终具有值 null。
因为 const 值在编译时是已知的,所以它们被允许作为 switch 语句中的 case 标签,作为可选参数的标准参数,作为属性规范的参数,等等。
如果在不同的程序集中使用 const 值,则必须注意版本控制。例如,如果程序集 A 定义了 public const int MaxRetries = 3;,而程序集 B 使用该常量,那么如果 MaxRetries 的值稍后在程序集 A 中更改为 5(然后重新编译),则该更改在程序集 B 中将无效,除非程序集 B 也被重新编译(参考新版本的 A)。
因此,如果某个值可能会在程序的未来版本中发生更改,并且该值需要公开显示,请不要声明该值 const,除非你知道每当更改某些内容时都会重新编译所有依赖程序集。替代方案是使用 static readonly 而不是 const,它在运行时解析。