C#泛型继承

Mic*_*han 4 c# generics polymorphism inheritance

我有以下课程

public class AccountingBase<TItemType> where TItemType : AccountingItemBase
Run Code Online (Sandbox Code Playgroud)

在我的AccountingItemBase中,我有以下属性:

public virtual AccountingBase<AccountingItemBase> Parent { get; set; }
Run Code Online (Sandbox Code Playgroud)

在我的AccountingBase中,我正在尝试执行以下操作

item.Parent = this;
Run Code Online (Sandbox Code Playgroud)

逻辑上这应该工作,因为TItemType继承自AccountingItemBase,但我得到以下错误:

> Error 1 Cannot implicitly convert type
> 'TGS.MySQL.DataBaseObjects.AccountingBase<TItemType>'
> to
> 'TGS.MySQL.DataBaseObjects.AccountingBase<TGS.MySQL.DataBaseObjects.AccountingItemBase>'
Run Code Online (Sandbox Code Playgroud)

如何将子属性父属性设置为自身(在父类内)

Jon*_*eet 6

不,你的直觉是不正确的.它不应该工作,因为泛型类在.NET中不是变体.

仅仅因为TItemType继承AccountingItemBase并不意味着AccountingBase<TItemType>继承自AccountingBase<AccountingItemBase>.假设AccountingBase<TItemType>有一个类型的字段TItemType.如果你的直觉是正确的,你可以写:

AccountingBase<SomeSubtype> x = new AccountingBase<SomeSubtype>();
AccountingBase<AccountingItemBase> y = x;
y.SomeField = new OtherSubtype();
Run Code Online (Sandbox Code Playgroud)

这显然会破坏类型的安全性,因为当看作是一个时AccountingBase<SomeSubtype>,字段意味着类型SomeSubtype,但你已经OtherSubtype在那里放了一个类型的值!

基本上,通用方差是一个复杂的主题.

我建议您阅读Eric Lippert的详细博客文章,了解更多信息.或者我有一个来自NDC 2010的视频,您可能会发现它很有用.基本上在.NET 4中存在一些通用差异,但它是有限的.

现在,关于你在你的情况下可以做些什么:

  • 您可以创建一个继承自的非泛型基类AccountingBase.这可能是最好的主意.然后创建Parent非泛型类型的属性.
  • 你可以AccountingBase在它自己和它的父亲中制作泛型......但这最终导致递归问题,有效......

  • @Alexander:不,但我喜欢将我的写作视为一种教学. (2认同)