为什么这个通用类型无法转换?

6

假设我有以下三个类/接口:

public interface IImportViewModel
{

}

public class TestImportViewModel : IImportViewModel
{

}

public class ValidationResult<TViewModel> where TViewModel : IImportViewModel
{

}

由于TestImportViewModel实现了IImportViewModel,为什么以下代码无法编译?
ValidationResult<IImportViewModel> r = new ValidationResult<TestImportViewModel>();

我理解 "无法隐式将类型 'ValidationResult' 转换为类型 'ValidationResult'" 的错误信息的意思。但我不明白为什么会出现这种情况。这不应该是协变吗?


2
我假设你的类_TestImportViewModel_应该是_TViewModel_?(上面的代码根本没有显示TViewModel类)。 - Sam Goldberg
是的。TestImportViewModel实现了IImportViewModel接口,因此应该能够作为TViewModel实现使用,如TViewModel:IImportViewModel。 - devlife
3
@Sam TViewmModel(又称<T>)是IImportViewModel类型的一种,它不是一个类。 - Renatas M.
1
@SamGoldberg,这是一个通用参数,通常被称为“T”,但在这种情况下有一个更具描述性的名称。 - Filip Ekberg
1
这里有一个类似问题的解释:https://dev59.com/Xm445IYBdhLWcg3w4-Be#4653199 - NaveenBhat
1个回答

8

这不就是协变吗?

是的,但在C# 4.0中,协变仅适用于接口。因此,您需要使您的ValidationResult实现一个协变接口(其中泛型参数定义为out):

public interface IImportViewModel
{
}

public class TestImportViewModel : IImportViewModel
{
}

public interface IValidationResult<out TViewModel> where TViewModel : IImportViewModel
{
}

public class ValidationResult<TViewModel> : IValidationResult<TViewModel> where TViewModel : IImportViewModel 
{
}

现在你可以这样做:

IValidationResult<IImportViewModel> r = new ValidationResult<TestImportViewModel>();

1
你仍然不能将值分配给 ValidationResult<IImportViewModel>,只能分配给 IValidationResult<IImportViewModel>。这很不幸。 - John Alexiou

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接