Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/292.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 加速实体框架4.2 POCO_C#_.net_Performance_Entity Framework - Fatal编程技术网

C# 加速实体框架4.2 POCO

C# 加速实体框架4.2 POCO,c#,.net,performance,entity-framework,C#,.net,Performance,Entity Framework,我使用的是实体框架4.2,我有一个相当严重的性能问题。我使用的是从DbContext继承的POCO方法,下面是一个解释问题的小示例: 我有一个数据库,它有两个表-a和B: A. AId(int-非null-标识-主键) 名称(nvarchar(50)-非空) B BId(整数-非空-标识-主键) SomeValue(int-非null) AId(int-非null-连接到表A中AId的外键) A有一行(1,“Test”),B有6000行(SomeValue只是一个从0到5999的数字)—

我使用的是实体框架4.2,我有一个相当严重的性能问题。我使用的是从DbContext继承的POCO方法,下面是一个解释问题的小示例:

我有一个数据库,它有两个表-a和B:

A.
  • AId(int-非null-标识-主键)
  • 名称(nvarchar(50)-非空)
B
  • BId(整数-非空-标识-主键)
  • SomeValue(int-非null)
  • AId(int-非null-连接到表A中AId的外键)
A有一行(1,“Test”),B有6000行(SomeValue只是一个从0到5999的数字)——所有这些都通过外键列引用A行

我从数据库创建一个edmx并关闭代码生成。然后创建以下类:

public class DatabaseContext : DbContext
{
    public DatabaseContext(string name) : base(name)
    {
        Configuration.AutoDetectChangesEnabled = false;
        As = Set<A>();
        Bs = Set<B>();
    }

    public DbSet<A> As { get; private set; }
    public DbSet<B> Bs { get; private set; }
}

public class A
{
    public virtual int AId { get; set; }
    public virtual string Name { get; set; }
    public virtual ICollection<B> Bs { get; private set; }

    public void AddB(B b)
    {
        if (b == null)
        {
            throw new ArgumentNullException("b");
        }

        if (Bs == null)
        {
            Bs = new List<B>();
        }

        if (!Bs.Contains(b))
        {
            Bs.Add(b);
        }

        b.A = this;
    }
}

public class B
{
    public virtual int BId { get; set; }
    public virtual A A { get; set; }
    public virtual int SomeValue { get; set; }
}
最后一行(在这里我添加了一个新的B)在我的四核4gb RAM 64位Windows7机器上花费了大约6秒的时间,该机器的数据库在本地运行

真正糟糕的是,它似乎呈指数级降级,因为如果将B中的行数增加一倍,则需要将近20秒


我真的很感激任何能让这更快发生的提示。非常感谢

导航属性的世界可能是一个痛苦的世界。我们基本上不得不逐步停止使用它们,因为它们会在背后造成太多性能问题(特别是当您连接和分离实体时,但情况不同)

发生的事情是,当你访问a.Bs时,它会为a加载所有的B


在这种特定情况下,如果您实际上不需要B的完整列表,而只想添加一个新列表,最好只创建一个B并将其辅助设置为a的ID。

在这种情况下,您应该禁用延迟加载:

var ctx = new DatabaseContext("ScalabilityTestEntities");
ctx.Configuration.LazyLoadingEnabled = false;
var a = ctx.As.FirstOrDefault();
a.Bs = new List<B>();
a.Bs.Add(new B { SomeValue = 987 });
var ctx=newdatabasecontext(“scalabilitytes”);
ctx.Configuration.LazyLoadingEnabled=false;
var a=ctx.As.FirstOrDefault();
a、 Bs=新列表();
a、 添加(新的B{SomeValue=987});
默认情况下,您启用了延迟加载(这会导致在访问集合时加载所有6000个B),因为您的导航集合被声明为
virtual
。如果您不需要或不想使用延迟加载,则应完全删除
virtual
关键字,或在上下文构造函数中禁用延迟加载

var ctx = new DatabaseContext("ScalabilityTestEntities");
ctx.Configuration.LazyLoadingEnabled = false;
var a = ctx.As.FirstOrDefault();
a.Bs = new List<B>();
a.Bs.Add(new B { SomeValue = 987 });