C# 是否可以阻止抽象类的继承

C# 是否可以阻止抽象类的继承,c#,inheritance,abstract-class,C#,Inheritance,Abstract Class,以代码为例: public abstract class Base { public Dictionary<int, string> Entities { get; private set; } protected Base() { Entities = new Dictionary<int, string>(); } } public abstract class A : Base { public abstract voi

以代码为例:

public abstract class Base
{
   public Dictionary<int, string> Entities { get; private set; }

   protected Base()
   {
      Entities = new Dictionary<int, string>();
   }
}

public abstract class A : Base
{
   public abstract void Update();
}

public abstract class B : Base
{
   public abstract void Draw();
}
公共抽象类基类
{
公共字典实体{get;private set;}
保护基()
{
实体=新字典();
}
}
公共抽象类A:基
{
公共摘要无效更新();
}
公共抽象类B:基
{
公开摘要无效抽取();
}

是否可以限制类(在同一程序集中)从
Base
继承,强制它们从
A
B
继承?

防止继承的唯一方法是像sealed一样声明类

public sealed abstract class A
{
}
但您将得到编译错误:

抽象类不能声明为密封类


这样做的原因是,对抽象类进行贴花并限制其继承树没有任何意义。Abstract类是一个实体,它的目标是由某人根据其定义进行扩展。

详细说明一下我的评论。这是不受支持的,所以答案是否定的。我想到的尝试这一点的唯一人为方法(这显然是行不通的)是拥有一个
密封的抽象类,这是毫无意义的,因为
a
B
,或其他任何东西都不能继承


例如,没有一个鉴别器允许我们说“sealed for”。

据我所知,你能做的最接近的事情是:

public abstract class Base
{
   internal Base()
   {
      // do stuff
   }
}
然后将
A
B
Base
移动到它们自己的程序集中。程序集之外的任何内容都可以看到
Base
,但无法直接扩展它,因为它无法访问构造函数

或者您可以执行运行时检查:

public abstract class Base
{
   protected Base()
   {
      if (!(this is A || this is B))
         // throw an exception
   }
}

我能想到的唯一解决办法是:

动态链接库

C.dll

然后在A.dll的AssemblyInfo.cs中使用[assembly:InternalsVisibleTo…],使内部类对B.ll可见


免责声明:它非常复杂,我不推荐它,但我想不出任何方法来满足您的约束。

不。那么
A
B
如何继承?您的意思是,您希望A和B继承Base,但不继承其他类?@crush是的,正是这样。这并不重要,但我很想知道这是否可能。将基类构造函数设置为私有,并将类A和B作为内部类添加到基类中。我对sealed进行了实验,得到了您描述和期望的错误。谢谢你的洞察力。非常感谢,因为你的评论是第一个,我会接受你的回答,谢谢。谢谢你的其他选择。第二个选择看起来真的不是一个好的编码方式。虽然适合手头的任务,扎伊茨曼我同意。我可能应该包括一个免责声明,说明这样做有多糟糕。
internal abstract class Base
{
   public Dictionary<int, string> Entities { get; private set; }

   protected Base()
   {
      Entities = new Dictionary<int, string>();
   }
}
public abstract class A : Base
{
   public abstract void Update();
}

public abstract class B : Base
{
   public abstract void Draw();
}
public class C : A
{
    public void Draw()
    {
    }
}