【问题标题】:Entity framework add record without checking if it exist or already added实体框架添加记录而不检查它是否存在或已添加
【发布时间】:2021-04-10 09:58:12
【问题描述】:

我有一个大型 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

我知道的任何方法都会使 EF 跟踪 Id 并查找重复项并减慢添加过程。我想要一种方法,我可以简单地添加范围而不检查重复项。如果在添加范围发生冲突,只需替换该项目。

类似

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

【问题讨论】:

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

标签: c# sql-server entity-framework large-data


【解决方案1】:

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

如果您希望使用实体框架尽可能快地批量添加行(这可能仍然比您的要求慢,但这还有待观察),那么您必须确保您的 id column 由实体框架自动生成,并且避免在每个批量插入的行中指定 id 的值。这样,实体框架将自己生成唯一的 id,因此根据您使用的数据库,它可能能够批量插入您的行,而无需检查每个 id 是否已经存在。

如果您的批量插入的行已经有一些您想要做一些有意义的事情的 id,您可能希望将这些 id 存储在一个单独的列中(例如,id2,),它没有被索引,所以它不会减慢批量插入,并在批量插入完成后执行额外查询,以查找重复项、将它们与现有行合并等。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-05-08
    • 2013-06-30
    • 1970-01-01
    • 1970-01-01
    • 2015-05-17
    • 1970-01-01
    相关资源
    最近更新 更多