C#抽象类静态字段继承

C#抽象类静态字段继承,c#,inheritance,static,field,abstract,C#,Inheritance,Static,Field,Abstract,我觉得我好像跳过了一两节C#类课程,但我的困境是: 我有一个抽象类,从中派生多个子类 我确信,对于每个子类,我都有一个构造函数,它需要一个特定的静态对象作为模型,并且每个子类的这个对象都是不同的 我的第一种方法是在抽象父类中创建一个公共静态对象,然后在我开始创建子类的任何实例之前,我会为每个子类修改它,但事实证明,这样我实际上只为抽象类创建一个静态对象,并且它的每个子类都使用它 我怎样才能解决这个问题 更准确地说,以下是伪代码: 父抽象类: abstract class AbstractCla

我觉得我好像跳过了一两节C#类课程,但我的困境是:

我有一个抽象类,从中派生多个子类

我确信,对于每个子类,我都有一个构造函数,它需要一个特定的静态对象作为模型,并且每个子类的这个对象都是不同的

我的第一种方法是在抽象父类中创建一个公共静态对象,然后在我开始创建子类的任何实例之前,我会为每个子类修改它,但事实证明,这样我实际上只为抽象类创建一个静态对象,并且它的每个子类都使用它

我怎样才能解决这个问题

更准确地说,以下是伪代码:

父抽象类:

 abstract class AbstractClass
{
   static public ModelObject Model;
   ...
}
其中一个子类:

class Child : AbstractClass
{
    ...
    public Child()
    {
        this.someField = Model.someField;
    }
}
编辑:

模型需要是“ModelObject”类的成员,而不应该是单例或任何其他类型

编辑2:

更确切地说,我为一个国际象棋游戏选择了这个实现:我有一个用于国际象棋棋子的抽象类,子类代表游戏的具体棋子:棋子、骑士等等

抽象类继承自MeshMatObject,该类表示具有基本功能的通用3d对象,如旋转、网格、材质、纹理等,并定义象棋棋子的抽象方法,如GetPossibleMoves()


我上面提到的模型对象是MeshMatObject的成员,在我看来,应该在类外定义一次,然后用于所有部分。我的意思是:例如,所有的棋子都有相同的网格和纹理,所以我不认为每次你想制作一个棋子时都要把一个模型作为一个参数有什么意义。

你可以通过使抽象类成为泛型来绕过共享的静态字段。每个泛型类将获得自己的静态字段副本

abstract class AbstractClass<T>
{
   static public ModelObject Model;
   ...
}
抽象类抽象类
{
静态公共模型对象模型;
...
}
然后每个子类将使用静态字段的不同实例

class Child : AbstractClass<Child>
{
    ...
    public Child()
    {
        this.someField = Model.someField;
    }
}
class子类:抽象类
{
...
公共儿童()
{
this.someField=Model.someField;
}
}

AbstractClass不引用泛型参数并不重要。您仅使用它为每个子类提供基类的唯一实例。

工厂如何将您的类与继承模型解耦:

public static class ModelObjectFactory
{
    public static ModelObject GetModel<T>(T obj)
    {
        // return ModelObject according to type of parameter
    }
}

class Child
{
    public Child()
    {
        ModelObject mo = ModelObjectFactory(this);
        this.someField = mo.someField;
    }
}
公共静态类ModelObjectFactory
{
公共静态模型对象GetModel(T obj)
{
//根据参数类型返回ModelObject
}
}
班童
{
公共儿童()
{
ModelObject mo=ModelObjectFactory(此);
this.someField=mo.someField;
}
}

我倾向于使用类似于@shf301的解决方案。根据您的需要,将基类设置为:

abstract class AbstractClass
{
}

abstract class AbstractClass<TModel> : AbstractClass
    where TModel : ModelObject 
{
   static public TModel Model;
   ...
}
抽象类抽象类
{
}
抽象类AbstractClass:AbstractClass
其中TModel:ModelObject
{
静态公共TModel模型;
...
}

这允许我在非泛型函数中使用公共基类。这也允许派生类型选择精确的模型类型,并且可以减少铸件。

AbstractClass需要以何种方式访问模型?您应该考虑将模型实例传递给子类的构造函数,而不是使用这样的静态字段。拥有静态模型确实违反了这里的封装精神。@dtb:抽象类实际上不需要访问模型。子类需要在其构造函数中访问它@Trillian:是的,这将是一个解决方案,实际上这是我的第一个实现,但是由于类的所有对象都是在相同的精确模型之后构建的,我认为最好只在类中定义一次模型,并使用静态字段来构造新实例。为什么它需要是静态的?你们在所有的类之间共享状态吗?谢谢你们的输入,它已经完成一半了。另一半来自Justin R。如果我只使用您的解决方案,我将无法仅使用AbstractClass对象进行操作。例如,我很难设计出一个抽象棋子的2D数组。无论如何,知道泛型类的每个孩子都会收到一个静态字段的副本是非常好的。工厂在其他情况下会工作得更好。在这个特殊的例子中,我想我会把情况复杂化(如果这是一个词的话);但是谢谢你的主意!拥有一个单一责任的对象不会使事情复杂化。检查坚实的原则-如果可能的话,我对评论说:)它工作得很好!只是“…”在“AbstractClass”上。这是一个很好且简单的实现,谢谢。还有一件事:这种实现是否会造成性能损失?我看不出有什么理由这样做,特别是VS的“优化代码”特性,但我只是确保。编辑:在我的例子中,类型约束应该是AbstractClass;然后子类将被声明为shf301所指出的。这是因为我只需要为AbstractClass的子级实现。类似于:AbstractClass:AbstractClass,其中T:AbstractClass和child:ChildClass:AbstractClass