【问题标题】:Ensuring static property is defined in derived classes确保在派生类中定义静态属性
【发布时间】:2018-07-14 09:50:55
【问题描述】:

我有一个要求,每个类都必须有一个静态只读属性以避免魔术字符串。最初,我想创建一个基类,强制每个派生类都实现静态只读属性。由于接口或抽象属性不能用于此目的。有没有办法在 C# 中实现这一点? 目前,我想到了以下解决方法,但我很容易看到它会导致未来的混乱,即,

基类

public abstract class Base
{
    public virtual string StaticProperty { get; }
}

派生类

public abstract class Derived : Base
{
    public new static string StaticProperty => "Some Value";
}

【问题讨论】:

  • 您的要求是什么?你能给我们一个具体的例子来说明你的代码应该如何使用吗?
  • @RuiJarimba 一个具体的例子可能是任何派生类都必须将表名作为静态字符串以避免魔术字符串。
  • 这感觉像是一个 XY 问题 - meta.stackexchange.com/questions/66377/what-is-the-xy-problem。为什么派生类型需要专门定义一个静态属性?
  • @ZerosAndOnes 不确定我是否理解您的问题,但请检查我的答案。

标签: c# static


【解决方案1】:

我不确定我是否理解您的问题,但我认为解决方案非常简单。你真的需要一个静态属性吗?如果没有,只需添加一个带参数的私有构造函数来初始化属性:

public abstract class Base
{
    public string StaticProperty { get; }

    protected Base(string staticProperty)
    {
        StaticProperty = staticProperty ?? throw new ArgumentNullException(nameof(staticProperty));
    }
}

然后,在派生类中,调用基础构造函数(否则会出现编译错误):

public class Derived : Base
{
    public Derived(string staticProperty) : base(staticProperty)
    {
    }
}

如您所见,如果不调用基本构造函数,您将收到编译错误:

【讨论】:

  • 谢谢,这让我朝着正确的方向前进,因为静态属性也可以在构造函数中访问。
【解决方案2】:

你的问题是没有约束强迫你实现它,所以在基类中定义它似乎是多余的。

不幸的是,替代方案同样有问题并且存在相同的问题,即您必须为每个派生类创建一个新分支。

public abstract class Derived : Base
{

}
public static class Helper<T> where T : Base
{
   public static string SomeProperty => GetMyProperty();

   public static string GetMyProperty()
   {
      if (typeof(T) == typeof(Derived))
      {
         return "asd";
      }

      throw new ArgumentOutOfRangeException();
   }
}

用法

var test = Helper<Derived>.SomeProperty;

// or

var test = Helper<Derived>.GetMyProperty();

另一种选择可能是使用属性,但这取决于您希望如何获取这些值,您仍然需要一个帮助程序或静态属性来检索它们

[MyAttribute("SomeName","SomethingElse")]
public abstract class Derived : Base

【讨论】:

    【解决方案3】:

    你说:

    一个具体的例子可以是任何派生类都必须将表名作为静态字符串以避免魔术字符串。

    所以你想确保这样一个属性存在大概是因为你想使用反射来访问它。编写一个反映所有此类类型的单元测试,并使用反射来确保它们包含静态属性。

    C# 类型系统在这里无法为您提供帮助。编写一个单元测试来断言这个结构。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-06-25
      • 2012-06-02
      相关资源
      最近更新 更多