【问题标题】:Using Concrete class as type parameter for inherited generic base class使用具体类作为继承的泛型基类的类型参数
【发布时间】:2011-10-06 16:44:28
【问题描述】:

我有一个带有以下签名的基类

public class ReportViewModelBaseDTO<VT,DT>

以及像这样的具体类

public class ChartViewModelDTO:ReportViewModelBaseDTO<ChartViewModel,ChartViewModelDTO>

我的问题是,我知道我的泛型基类的第二个类型参数应该是具体类的类型。我不想通过命名类然后重复该名称作为类型参数来重复自己。

有没有办法让我的通用基类将实际的具体类作为类型参数?有人对更好的方法有什么建议吗?

编辑:

我想如何使用 DT 的示例如下。我通过 Automapper 从 VT 类型之一创建了一个 DT 类型的实例。

public static DT Create(VT viewModel)
        {
            return Mapper.Map<VT,DT>(viewModel);   
        }

【问题讨论】:

  • 你能提供一个你想如何使用DT的用例吗?基类需要知道它是哪个具体实现的基类,这感觉有点奇怪。我可以看到一些用途(例如从方法返回正确的类型),但不是很多。
  • C# 无法强制执行您似乎想要的要求,将基类的泛型 T 强制为派生类的类型。请参阅this related question 了解更多信息。

标签: c# .net generics inheritance


【解决方案1】:

这是你的意思吗?

public class ReportViewModelBaseDTO<VT,DT> where DT : ReportViewModelBaseDTO<VT,DT>

现在您的类“知道”第二个类型参数是其自身的具体实现。

对于您的示例方法,您可以这样做:

public static DT Create(VT viewModel)
{
  return Mapper.Map<VT, DT>(viewModel);   
}

并将Mapper.Map 定义为:

private U Map<T, U>(ViewModel viewModel) where U : ReportViewModelBaseDTO<T,U>{...}

【讨论】:

  • 知道,还是仅仅假设?考虑class Animal&lt;T&gt; where T : Animal&lt;T&gt; { } class Cat : Animal&lt;Cat&gt; { } class Dog : Animal&lt;Cat&gt; { } 这是合法的。 C# 无法强制要求只有 Cat 可以从 Animal&lt;Cat&gt; 继承。
  • 不完全是,我希望我的基类知道派生类是什么类型,以便我可以在返回方法中使用该类型,例如我编辑中的方法
  • 使 Map 通用,即 Mapper.Map(...) 然后您可以让 Map 返回正确的类型。
  • Lerxst... GetType() 将返回类的类型(不是基类)... 即 public class Cat : Animal { ... } 任何调用 GetType 的代码都会返回 Cat 作为类型。
  • 这就是我打算做的,但是方法是静态的,所以我不能使用 GetType()
猜你喜欢
  • 1970-01-01
  • 2012-11-29
  • 2015-11-18
  • 2012-08-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多