我的EF 4.3.1模型有200多个表。最初的启动很糟糕,几分钟。 DotTrace捕获的配置文件暗示了框架深处的一些可怕的算法/可伸缩性选择,正如数百万次调用那里的许多方法和3600万个IEnumerable.Contains()调用所证明的那样。这是一个片段,这是由在数据库上完成的第一个查询触发的(未来的查询不会这样做并且很好)。
我可以对我的模型做些什么来减轻痛苦?我能以某种方式预先编译吗?更好的是,EF团队可以解决这些问题或开源框架,以便我可以吗?或者至少修正Warapper
的拼写? :)
编辑:触发此操作的一个特定EF调用基本上是var db = new MyDbContext(); db.Personnel.Where(a => a.Login == login).SingleOrDefault();
。此外,EF Migrations Seed()AddOrUpdate可以有效地生成相同的堆栈。可以提供更多上下文的更全面的堆栈跟踪在这里:Fuller Stack Trace
编辑:一些相关链接:
EDIT2:现在他们只是open sourced代码,看来这一行:
//Filter the 1:1 foreign key associations to the ones relating the sets used in these cell wrappers.
oneToOneForeignKeyAssociationsForThisWrapper =
oneToOneForeignKeyAssociationsForThisWrapper.Where(
it => (it.AssociationEndMembers.All(endMember => entityTypes.Contains(endMember.GetEntityType()))));
是需要一些工作的人。它可能没有使用O(n ^ 2)算法,但我还没有仔细观察。
EDIT3:令人高兴的是,看起来EF6中的工作正在修复此代码:http://entityframework.codeplex.com/discussions/396130
答案 0 :(得分:23)
在EF6之前,已知视图生成对于较大型号而言较慢。目前解决方案是使用预生成的视图。这样,您可以在设计时生成视图,并在运行时避免这种工作。为此,请下载EF电动工具并选择“优化实体数据模型”。它会将C#文件添加到包含视图的项目中。不好的一面是,每次模型更改时都需要这样做。注意:要使用该工具生成视图,它将花费大约相同的时间在运行时生成视图(因此有时您需要耐心等待)。以下是可能有用的EF Power Tools帖子:http://blogs.msdn.com/b/adonet/archive/2011/05/18/ef-power-tools-ctp1-released.aspx
修改强>
最近我创建了一个更方便使用的不同解决方案(注意它只适用于EF6) - http://blog.3d-logic.com/2013/12/14/using-pre-generated-views-without-having-to-pre-generate-views-ef6/
答案 1 :(得分:12)
这是另一种方法。它需要一些手动工作,但实际上可能更适合您想要使用MsBuild的场景。而不是使用Power Tools创建视图(我很遗憾听到它们不适合您),您可以手动创建它们 - 以下是步骤:
var ms = new MemoryStream();
using (var writer = XmlWriter.Create(ms))
{
EdmxWriter.WriteEdmx(new Context(), writer);
}
ms.Position = 0;
var xDoc = XDocument.Load(ms);
var ssdl = xDoc.Descendants("{http://schemas.microsoft.com/ado/2009/02/edm/ssdl}Schema").Single();
var csdl = xDoc.Descendants("{http://schemas.microsoft.com/ado/2008/09/edm}Schema").Single();
var msl = xDoc.Descendants("{http://schemas.microsoft.com/ado/2008/09/mapping/cs}Mapping").Single();
ssdl.Save("Context.ssdl");
csdl.Save("Context.csdl");
msl.Save("Context.msl");
EdmGen /mode:ViewGeneration /incsdl:Context.csdl /inmsl:Context.msl /inssdl:Context.ssdl /outviews:Context.Views.cs
如果要将视图生成与构建系统集成,还有一个有趣的选项 - 使用T4模板。该模板将处理上述步骤。您可以在http://blogs.msdn.com/b/adonet/archive/2008/06/20/how-to-use-a-t4-template-for-view-generation.aspx找到有关此方法的更多详细信息。唯一的问题是该示例不适用于CodeFirst方法,因此需要稍微更改一下,这应该不会很难。
我实际上为Code First创建了T4模板。您可以在我的博文中找到要下载的链接:http://blog.3d-logic.com/2012/05/28/entity-framework-code-first-and-pre-generated-views/
现在可以在Visual Studio代码库中使用这些模板。以下是包含所有详细信息的帖子的链接:http://blog.3d-logic.com/2012/06/13/entity-framework-codefirst-view-generation-templates-on-visual-studio-code-gallery/
答案 2 :(得分:1)
在当前版本的Entity Framework中,视图生成实际上非常快。 (6.1)准备中还有另一个更广泛的缓存解决方案:https://entityframework.codeplex.com/workitem/1876。你可以等待这个补丁被接受,或者,如果你足够勇敢,你可以自己申请。