抽象类中的静态方法返回IEnumerable <derivedtype> </derivedtype>

时间:2011-07-12 15:15:47

标签: c# generics

有没有办法将静态方法放在可以返回派生类型的抽象类中?

静态方法是否知道甚至在C#中调用它的类型?

例如,基类可以是

public abstract class MyBase
{
    public static IEnumerable<TDerivedType> LoadAll()
    {
        //functionality here
    }
}

如果MyDerivedType继承MyBase,我希望能够致电MyDerivedType.LoadAll()

没什么太重要的 - 我现在正在使用通用的静态方法并调用MyBase.LoadAll<MyDerivedType>(),它工作得很好,但它看起来并不像那样“漂亮”。

4 个答案:

答案 0 :(得分:4)

静态成员不是继承的,因此必须以某种方式告诉静态方法派生类型是什么。您的解决方案是一种方式。另一个是:

public abstract class MyBase<T> where T : MyBase<T> {
    public static IEnumerable<T> LoadAll() { }
}

然后:

class Derived : MyBase<Derived> { }

var all = MyBase<Derived>.LoadAll();

那就是说,我认为你的模型有问题。 MyBase表示域中的某些内容(它们是更具体的派生类型)并且它知道如何加载所有这些对象?这是两个责任,这不是很酷的哟。

答案 1 :(得分:2)

不,目前还没有办法做到这一点。在这种情况下,我可能会使用工厂

var all = MyClassFactory.LoadAll<MyDerivedType>();

答案 2 :(得分:1)

永远不能实例化抽象类(这就是重点),因此必须在每个子类中实现任何静态方法。

来自an MSDN Thread

  

静态方法可以在抽象类中定义。但是,您不能强制派生类实现静态方法。如果你考虑一下,这样的方法就没用了。使用类型名称而不是实例变量调用静态方法。如果我调用MyBaseClass.MyMethod,那么将始终调用MyBaseClass.MyMethod。如何强制从MyBaseClass继承MyChildClass,以及实现静态MyMethod?

(注意:编辑实现在第一句中实例化。)

答案 3 :(得分:0)

你这样做的方式没有错。事实上,大多数MS通用扩展方法都是这样设计的。

至于:

“静态方法是否知道甚至在C#中调用它的类型?”

它不是静态方法知道的问题,它是编译器知道的问题。当编译器扫描代码时,这是合并所有类型的时间。此时,它可以确定哪些代码调用哪些函数以及需要返回哪些类型。这也是无法从函数返回var类型的原因。