C# 实体框架添加记录,而不检查记录是否存在或已添加

C# 实体框架添加记录,而不检查记录是否存在或已添加,c#,sql-server,entity-framework,large-data,C#,Sql Server,Entity Framework,Large Data,我有一个很大的CSV文件,需要从中向数据库添加项目(超过一百万行)。我已将原始csv分块,将行输入限制为每次1000行。我已经尝试了一些添加到Db的逻辑 var modelObjects = new List<ModelObject>(); ... add 1000 rows to modelObjects context.ModelObjects.AddRange(ModelObjects); context.SaveChanges(); ... repeat until all

我有一个很大的CSV文件,需要从中向数据库添加项目(超过一百万行)。我已将原始csv分块,将行输入限制为每次1000行。我已经尝试了一些添加到Db的逻辑

var modelObjects = new List<ModelObject>();
... add 1000 rows to modelObjects
context.ModelObjects.AddRange(ModelObjects);
context.SaveChanges();
... repeat until all data is added to db
var modelObjects=new List();
... 向modelObjects添加1000行
context.ModelObjects.AddRange(ModelObjects);
SaveChanges();
... 重复此操作,直到所有数据都添加到数据库中
我所知道的任何方法都会使EF track Id和查找重复项并减慢additon过程。我想要一种方法,我可以简单地添加范围,而无需检查重复项。如果在AddingRange上发生冲突,只需替换该项即可

差不多


context.ModelObjects.AddRange(ModelObjects)--force--ignoreduplicatecheck

正如您所观察到的,当行包含id时,批量添加行的速度非常慢,因为实体框架除了检查每个id是否已经存在之外别无选择

如果您希望使用entity framework以尽可能快的速度批量添加行(这可能仍然比您的要求慢,但这还不清楚),那么您必须确保您的id列是由entity framework自动生成的,并且不要在每个批量插入行中指定id的值。这样,entity framework将自己生成唯一的id,因此根据您使用的数据库,它可能能够批量插入您的行,而无需检查每个id是否已经存在


如果大容量插入的行已经有一些ID,您希望对这些ID执行一些有意义的操作,您可能希望将这些ID存储在一个单独的列中(例如,
id2
),该列没有索引,因此不会减慢大容量插入的速度,并在大容量插入完成后执行额外的查询以查找重复项,将它们与现有行合并,等等。

我的建议:如果要添加那么多记录,不要使用实体框架。对于所有批量操作,都有更好的工具。将EF留给CRUD操作。EF是一个很好的工具,但它不是一个银弹。在这种情况下,我会放弃使用EF,而直接使用Sql批量插入、带有表值参数的ADO.NET或SqlCmd.exe。我认为EF不是添加1mln行的最佳工具。如果您使用直接批量t-sql脚本或第三方UTIL,您应该使用ADO.NET甚至更好。我建议使用sql批量插入。您有权修改数据库架构吗?您可以让EF调用一个插入数据的存储过程。是时候执行sql bluck insert或insert了。将其全部插入临时表,然后使用SQL合并来处理重复数据等。