2

假设我有两个类,一个派生自另一个:

动物和狗

public class Animal
{
    public String Name { get; set; }
}

public class Dog : Animal
{
    public Boolean HasSpots { get; set; }
}

在我的控制器中,我将动物传递给索引视图

public ActionResult Index()
{
    return View(new Dog() {Name = "Dog"});
}

索引 - 我将传入的 Animal 转换为带有 Dog 的编辑器模板。

@model MvcApplication1.Models.Animal

@using (Html.BeginForm("About", "Home", FormMethod.Post, null))
{
    @Html.EditorFor(x =>  x, "Dog", "Animal")

    <input type="submit" value="Begin" />
}

这可以正常工作,但是当我尝试在控制器中显式转换回 Dog 时,当我将其发布到 About 时,它不会转换。我想象我将不得不创建一个自定义模型绑定器,但我不知道如何做到这一点。或者,如果我只是完全错过了一些东西。在不包括接口的情况下解决这个问题。

(使用这个作为一个小测试示例,我的实际类要复杂一些)

4

1 回答 1

5

默认模型绑定器不会尝试猜测您是否发布了比预期更多的派生类。因此,即使您的表单具有更多派生类的字段,如果该操作期望类动物,它将创建动物并且您将无法强制转换为狗,因为从未创建过狗。

我看不到界面可以在这里为您提供帮助。如果您让您的操作接受接口或抽象类,则默认模型绑定器将由于无法实例化所述类型而引发异常。

自定义模型绑定器可以为您处理这种情况。我见过的所有方法都涉及将一些额外的元数据加入到混合中。

使用附加表单字段来保存实际类型的示例在这里。 带有 List<BaseClass> 和编辑器模板的 ViewModel

这里有一个使用属性来执行某种“已知类型”的示例。http://mvccontrib.codeplex.com/wikipage?title=DerivedTypeModelBinder&referringTitle=Documentation

于 2012-11-18T21:14:16.910 回答