Asp.net mvc 填充对象的简单方法

Asp.net mvc 填充对象的简单方法,asp.net-mvc,architecture,entity-framework-6,Asp.net Mvc,Architecture,Entity Framework 6,我有以下课程: public class SectionViewModel { private static EFModels.VTSEntities _db = new EFModels.VTSEntities(); public int ID { get; set; } public string SectionName { get; set; } public bool Active { get; set; }

我有以下课程:

    public class SectionViewModel
    {
        private static EFModels.VTSEntities _db = new EFModels.VTSEntities();
        public int ID { get; set; }
        public string SectionName { get; set; }
        public bool Active { get; set; }
        public string SiteName { get; set; }
   }
我想从_db.Sections中选择一个元素并填充这个类的对象。我可以这样做:

    public SectionViewModel(int ID)
    {
        var s = (from i in _db.Sections
                 where i.ID == ID
                 select new SectionViewModel()
                 {
                     ID = i.ID,
                     SectionName = i.SectionName,
                     Active = i.Active,
                     SiteName = i.Site.SiteName
                 }).FirstOrDefault();
        ID = s.ID;
        SectionName = s.SectionName;
        Active = s.Active;
    }
它可以工作,但当字段数为十时,代码是巨大的。我想写一些类似的东西

    // IT DOES NOT WORK, ONLY EXAMPLE
    public SectionViewModel(int ID)
    {
        this = (from i in _db.Sections
                 where i.ID == ID
                 select new SectionViewModel()
                 {
                     ID = i.ID,
                     SectionName = i.SectionName,
                     Active = i.Active,
                     SiteName = i.Site.SiteName
                 }).FirstOrDefault();
    }
增加:

创建SectionViewModel对象(它是一个视图模型类):

但是,当然,这是不可能的,因为“this”只能用于阅读。有什么办法吗?

编辑

好的,那么您将从
构造一个
节视图模型
,而不是
。这会有一些不同,但我的原始答案中仍有许多评论适用

更好的方法是

public ActionResult SectionForm(int id)
{
    Section section = this._context.Sections.Find(id);
    SectionViewModel model = .... // Mapping code
    return View(model);
}
此部分
//映射代码
可以是将属性从
部分
复制到
模型
的任何内容。你可以用AutoMapper

SectionViewModel
的构造函数中不这样做的原因是首先不应该存在静态上下文。您可以创建和处理上下文来代替。但是谁说
SectionViewModel
s总是单独构建的呢?也许在另一种方法中,您将返回它们的列表。单独创建每个模型将非常低效。这种方法在那里是合适的


原文

在构造函数中构造一个对象(这是由部分
var s=(…).FirstOrDefault()
)发生的事情)然后将其属性复制到构造函数的所有者(类型相同,
)。更荒谬的是,在查询中,您还从一个节构造了一个
节。所以在运行声明之后

Section model = new Section(id);
…您已经构建了三个相同的
部分,最后一个部分被最终使用:

第1节:
来自i in\u db.Sections,其中i.ID==ID选择i

第2节:
选择新节(){…}

第3节:
节(内部ID)

EF甚至不允许这样的声明

from i in _db.Sections
select new Section() {...}
它将告诉您不能在LINQtoEntities查询中构造实体

但是删除这个
selectnewsection(){…}
甚至不是声音重构的开始。整个结构是荒谬的

另一个糟糕的做法是使用静态上下文。上下文的设计寿命很短,因为它们缓存从数据库中获取的每个实体。静态上下文是内存泄漏

实现你想要的方法很简单

public ActionResult SectionForm(int id)
{
    Section model = this._context.Sections.Find(id);
    return View(model);
}
…其中,
this.\u context
是您的
vtSenties
的一个实例,该实例是根据控制器实例创建的(或通过控制容器的反转注入)


您的编程风格让人隐约联想到一种与EF的存储库/工作单元模式(其中,
DbSet
是一种repo,
DbContext
是一种UoW)不能很好地混合的模式。它还打破了EF赖以建立的持续无知原则。它破坏了查询的可组合性,并且很容易导致
n+1
查询。

@Gert Arnold,我补充道,如果我正确理解您的问题,这就是为什么会存在类似产品。我建议您阅读如何使用MVC+EF。您的代码是错误模式的密集集合,显然是受到过去编程传统的微弱回响的启发。回到绘图板上,我读了很多这样的文章。你能描述一下为什么我的方法是错误的吗?如果有必要,我只想在构造函数中填充我的视图模型。哪种模式被破坏了?我的分区类是视图模型类,而不是EF类!所以,你的例子不合适。为了更清楚,我将在问题中删除Section类到SectionViewModel!使用EF模型类进行查看是非常糟糕的方法(我可以在您的控制器方法中看到)。EF模型是EF模型,视图模型是视图模型!请参阅修改后的答案。如果我想从2个或更多实体(即SectionViewModel由节填充,一个参数由站点填充),您的方法不合适。请指出一种情况,为什么您的方法不好。您建议获取模型类的对象,然后复制到视图模型类的对象。
public ActionResult SectionForm(int id)
{
    Section model = this._context.Sections.Find(id);
    return View(model);
}