ASP.NET MVC 3视图,超类不适用于子类?

时间:2012-10-07 22:45:47

标签: asp.net-mvc asp.net-mvc-3 razor asp.net-membership covariance

我有以下课程 -

public abstract class BusinessObject { }
public abstract class Form: BusinessObject { }
public abstract class BillableForm: Form { }
public class MembershipForm: BillableForm { }

public abstract class Dto<T>: where T: BusinessObject { }
public abstract class InboxDto<T>: Dto<T> where T: Form { }
public class MembershipFormDto: InboxDto<MembershipForm> { }

我有以下观点 -

membershipform.cshtml:
@model AdminSite.Models.MembershipFormDto
@{
    Layout = "~/Views/Inbox/Shared/_LayoutForm.cshtml"
}

_LayoutForm.cshtml:
@model InboxDto<Form>

当我登上membershipform.cshtml页面时,我收到以下异常说明:

传递到字典中的模型项类型为&#39; AdminSite.Models.MembershipFormDto&#39;,但此字典需要类型为&#39; AdminSite.Infrastructure.Models.InboxDto`1的模型项[BusinessLogic .Inbox.Form]&#39;

从我能说的一切MembershipFormDto IS-A InboxDto类型为MembershipForm,其中MembershipForm IS-A Form。是什么给了什么?

1 个答案:

答案 0 :(得分:2)

这是一个协方差问题。

我添加了以下界面 -

public interface IInboxDto<out T>

并修改了InboxDto类以实现该接口 -

public abstract class InboxDto<T>: Dto<T>, IInboxDto<T> where T: Form { }

简而言之,协方差从更明确的类型转变为不太明确的类型;特别是使用定义较少的引用引用更定义的对象。编译器抱怨的原因是它阻止了这样的场景:

List<String> instanciatedList = new List<String>;
List<Object> referenceList = instanciatedList;
referenceList.add(DateTime);

最后一行是有道理的,DateTime IS-A Object。我们已经说referenceListList的{​​{1}}。然而,它被定为Object ListString List ObjectList String更宽松。突然间,new List<String>的保证被忽略了。

然而,Interface定义的out和in关键字告诉编译器放松,我们知道我们正在做什么,并了解我们正在做什么。

More information.