在C#中实现全局常量的最佳方法是什么?

The*_*ght 10 c# asp.net resources constants readonly

我有一个Common项目,我在其中添加了QueryStringNames的公共常量.

我知道一般常量应该是内部的或私有的,但我需要公共常量,因为我想允许全局访问查询字符串名称,会话密钥等.

我知道有3种解决方案,但它们都有一个重要的问题.调用程序集将包含my常量的副本,这意味着如果我必须更改常量值,我将必须编译我的Common程序集和调用程序集程序!

1) public const string ConstName = "a value";
2) public readonly string ConstName = "a value";
3) To be stored in a public resource file.
Run Code Online (Sandbox Code Playgroud)

除了将它们存储在web.config文件(没有intellisense)之外,在C#中定义公共常量的最佳方法是什么?

Cod*_*aos 6

这取决于.如果它真的是一个不会改变的常量,即使在你的代码的未来版本中,那const也没关系.否则去一个static readonly领域.

A const将嵌入到调用程序集中,而static readonly调用程序集只包含对该字段的引用.这意味着const每当您更改值时都需要重新编译所有相关代码,而public readonly即使不重新编译调用程序集也会使用新值.

如果要将"常量"存储在配置文件中,但是像Intellisense一样,则可以使用不带公共设置器的属性.然后在运行时从配置文件中填充它.但我认为配置值不应该static放在第一位.对于配置值,我会使用某种单体,最好是IoC变化,而不是Class.Instance变化.所以我只需要定义如下界面:

interface IMyConfig
{
  string Key{get;}
}
Run Code Online (Sandbox Code Playgroud)

并且需要此配置的类将其作为构造函数参数:

public MyClass(IMyConfig config)
{
    ...
}
Run Code Online (Sandbox Code Playgroud)

  • @William默认情况下,你可能会对VS重建所有依赖程序集感到困惑.但是,如果您使用包含程序集的新"静态只读"并简单地用不同版本替换该单个dll,则构建在其上的所有程序集仍然可以工作,并使用新值. (2认同)

Jef*_*Fay 6

如果你认为你要改变它并且你担心必须编译它,那么为什么不在web配置文件中使用appSettings?这就是它的用途.如果你真的需要intellisense,那么你可以将一个类放在一个读取配置值的程序集中,并将其公开为一个属性,以便于引用.如果它是敏感数据,那么我不会把它放在配置文件中,我只是编译它,因为你不想妥协你的应用程序.

<appSettings>
    <add key="myconstant" value="here's the value!" />
</appSettings>
Run Code Online (Sandbox Code Playgroud)

这是引用该值的类,它为您提供智能感知,能够在将来轻松更改它,而无需重新编译任何内容

public class MyAppConfigSettings
{
    public string MyConstant { get; private set; }

    public MyAppConfigSettings()
    {
        MyConstant = ConfigurationManager.AppSettings["myconst"];
    }
}
Run Code Online (Sandbox Code Playgroud)

它可能不是您的解决方案的答案,但它可能会给您一些其他的想法.


小智 2

如果您正在激活 fxCop(Visual Studio 发行版中包含的代码分析工具),您可能会收到将常量更改为的建议:

公共静态只读字符串ConstName =“一个值”;

  • 我手头没有编译器,但令我惊讶的是,考虑到“const”值的性质,“static”关键字是必需的,甚至是合法的。 (3认同)