What is the difference between const
and readonly
and do you use one over the other?
相关问题
- Sorting 3 numbers without branching [closed]
- Graphics.DrawImage() - Throws out of memory except
- Generic Generics in Managed C++
- Why am I getting UnauthorizedAccessException on th
- 求获取指定qq 资料的方法
I believe a
const
value is the same for all objects (and must be initialized with a literal expression), whereasreadonly
can be different for each instantiation...One thing to add to what people have said above. If you have an assembly containing a readonly value (e.g. readonly MaxFooCount = 4; ), you can change the value that calling assemblies see by shipping a new version of that assembly with a different value (e.g. readonly MaxFooCount = 5;)
But with a const, it would be folded into the caller's code when the caller was compiled.
If you've reached this level of C# proficiency, you are ready for Bill Wagner's book, Effective C#: 50 Specific Ways to Improve Your C# Which answers this question in detail, (and 49 other things).
A
const
has to be hard-coded, where asreadonly
can be set in the constructor of the class.Constant variables are declared and initialized at compile time. The value can’t be changed after wards. Read-only variables will be initialized only from the Static constructor of the class. Read only is used only when we want to assign the value at run time.
Apart from the apparent difference of
const
VSreadonly
values can be computed dynamically but need to be assigned before the constructor exits.. after that it is frozen.static
. You use aClassName.ConstantName
notation to access them.There is a subtle difference. Consider a class defined in
AssemblyA
.AssemblyB
referencesAssemblyA
and uses these values in code. When this is compiled,const
value, it is like a find-replace, the value 2 is 'baked into' theAssemblyB
's IL. This means that if tomorrow I'll updateI_CONST_VALUE
to 20 in the future.AssemblyB
would still have 2 till I recompile it.readonly
value, it is like aref
to a memory location. The value is not baked intoAssemblyB
's IL. This means that if the memory location is updated,AssemblyB
gets the new value without recompilation. So ifI_RO_VALUE
is updated to 30, you only need to buildAssemblyA
. All clients do not need to be recompiled.So if you are confident that the value of the constant won't change use a
const
.But if you have a constant that may change (e.g. w.r.t. precision).. or when in doubt, use a
readonly
.Update: Aku needs to get a mention coz he pointed this out first. Also I need to plug where I learned this.. Effective C# - Bill Wagner
There is a small gotcha with readonly. A readonly field can be set multiple times within the constructor(s). Even if the value is set in two different chained constructors it is still allowed.