C# 传递到字典中的模型项的类型为。。但此词典需要类型为的模型项

C# 传递到字典中的模型项的类型为。。但此词典需要类型为的模型项,c#,asp.net-mvc,C#,Asp.net Mvc,添加此问题和社区wiki答案是为了帮助解决中讨论的大量未回答问题。 我有一些代码,当它执行时,会抛出一个异常,说: 传递到字典中的模型项的类型为Bar,但此字典需要类型为Foo的模型项 这意味着什么,我如何修复它?错误意味着您正在导航到一个视图,该视图的模型声明为typeofFoo(通过使用@model Foo),但实际上您传递了一个typeofBar(注意,之所以使用术语词典,是因为模型是通过ViewDataDictionary传递给视图的) 错误可能由以下原因引起: 将错误的模型从控制器方

添加此问题和社区wiki答案是为了帮助解决中讨论的大量未回答问题。


我有一些代码,当它执行时,会抛出一个异常,说:

传递到字典中的模型项的类型为Bar,但此字典需要类型为Foo的模型项


这意味着什么,我如何修复它?

错误意味着您正在导航到一个视图,该视图的模型声明为typeof
Foo
(通过使用
@model Foo
),但实际上您传递了一个typeof
Bar
(注意,之所以使用术语词典,是因为模型是通过
ViewDataDictionary
传递给视图的)

错误可能由以下原因引起:

将错误的模型从控制器方法传递到视图(或局部视图)

常见示例包括使用创建匿名对象(或匿名对象集合)的查询并将其传递给视图

var model=db.Foos.Select(x=>new
{
ID=x.ID,
Name=x.Name
};
返回视图(模型);//将匿名对象传递给使用@model Foo声明的视图
或者将一组对象传递给需要单个对象的视图

var模型=db.Foos.Where(x=>x.ID==ID);
返回视图(模型);//将IEnumerable传递给使用@model Foo声明的视图
通过在控制器中显式声明模型类型以匹配视图中的模型,而不是使用
var
,可以在编译时轻松识别错误

将错误模型从视图传递到局部视图

@model IEnumerable<WFAccess.Models.ViewModels.SiteViewModel>

<div class="row">
    <table class="table table-striped table-hover table-width-custom">
        <thead>
            <tr>
....
给定以下模型

公共类Foo
{
公共栏MyBar{get;set;}
}
以及使用
@model Foo
声明的主视图和使用
@model Bar
声明的局部视图,然后

Foo model=db.Foos.Where(x=>x.ID==ID).Include(x=>x.Bar).FirstOrDefault();
返回视图(模型);
将向主视图返回正确的模型。但是,如果视图包含

@Html.Partial(“\u-Bar”)//或@Html.RenderPartial(\u-Bar”)}
默认情况下,传递到局部视图的模型是在主视图中声明的模型,您需要使用

@Html.Partial('u-Bar',Model.MyBar)//或@Html.RenderPartial('u-Bar',Model.MyBar);}
要将
Bar
的实例传递给部分视图,请注意,如果
MyBar
的值为
null
(尚未初始化),则默认情况下
Foo
将传递给部分视图,在这种情况下,需要对其进行初始化

@Html.Partial(“\u-Bar”,new-Bar())
在布局中声明模型

如果布局文件包含模型声明,则使用该布局的所有视图都必须声明相同的模型或从该模型派生的模型


如果要在版面中包含单独模型的html,则在版面中,使用
@html.Action(…)
调用
[ChildActionOnly]
方法初始化该模型并返回其部分视图。

观察视图是否具有所需的模型:

查看

@model IEnumerable<WFAccess.Models.ViewModels.SiteViewModel>

<div class="row">
    <table class="table table-striped table-hover table-width-custom">
        <thead>
            <tr>
....
@model IEnumerable
....
控制器

[HttpGet]
public ActionResult ListItems()
{
    SiteStore site = new SiteStore();
    site.GetSites();

    IEnumerable<SiteViewModel> sites =
        site.SitesList.Select(s => new SiteViewModel
        {
            Id = s.Id,
            Type = s.Type
        });

    return PartialView("_ListItems", sites);
}
[HttpGet]
公共操作结果列表项()
{
SiteStore站点=新建SiteStore();
site.GetSites();
IEnumerable站点=
site.SitesList.Select(s=>new SiteViewModel
{
Id=s.Id,
类型=s.类型
});
返回PartialView(“列表项”,站点);
}

在我的例子中,我使用局部视图,但在正常视图中运行

这个问题已经有了一个很好的答案,但我在不同的场景中遇到了相同的错误:在EditorTemplate中显示一个
列表

我有一个这样的模型:

public class Foo
{
    public string FooName { get; set; }
    public List<Bar> Bars { get; set; }
}

public class Bar
{
    public string BarName { get; set; }
}
这是我的Bar编辑模板(Bar.cshtml)

并将编辑器模板(Bar.cshtml)更改为:

@模型栏
@Model.BarName

考虑
Partials/map.cshtml
上的分部
map.cshtml
。只需使用
标记,即可从要呈现分部的页面调用:


这是我遇到的最简单的方法之一(尽管我使用的是razor pages,我相信MVC也是如此)

这与问题有什么关系?@StephenMuecke This champs-传入字典的模型项是Bar类型的,但此字典需要一个Foo+1类型的模型项用于还请注意,如果MyBar的值为null(尚未初始化),那么默认情况下,Foo将被传递给partial,在这种情况下,它需要"。非常重要的一点。我在布局中有一个部分视图,但没有定义模型类型,因此我得到了相同的错误。部分视图崩溃,因为它从索引页接收模型,但没有定义也不需要。如果我将部分模型设置为IndexModel,那么ViewData属性为null!?如何修复此场景?移动p布局中的artial确实有效,但我想了解它是如何工作的。当我的局部视图顶部有“@page”而没有“@model”时,我遇到了相同的错误。删除“@page”解决了问题。如果你想在
model.MyBar
为null时故意向局部视图发送null模型,你可以这样做:
@Html.partial(“\u Bar”,Model.MyBar,new System.Web.Mvc.ViewDataDictionary())
来源:@Smix这是一个非常有用的评论。我遇到了这个问题。我在使用
返回视图
而不是
返回部分视图
时遇到了这个错误,所以这也需要检查
是否有效:)太棒了,半个小时后你救了我一命。也适用于ASP.NET Core 3.1 MVC。
@model List<Bar>

<div class="some-style">
    @foreach (var item in Model)
    {
        <label>@item.BarName</label>
    }
</div>
@model Foo

@Html.TextBoxFor(m => m.Name, new { @class = "form-control" })  
<div class="some-style">
    @Html.EditorFor(m => m.Bars)
</div>
@model Bar

<label>@Model.BarName</label>