更快的SQL插入?

时间:2010-09-08 14:47:55

标签: c# sql-server linq bulkinsert

我正在处理每个50k行的数据块。 我正在使用LINQ:

将它们插入到SQL数据库中
for(int i=0;i<50000;i++)
{
    DB.TableName.InsertOnSubmit
    (
        new TableName
        {
            Value1 = Array[i,0],
            Value2 = Array[i,1]
        }
    );
}
DB.SubmitChanges();

这需要大约6分钟,如果可能的话,我希望它花费更少。有什么建议吗?

3 个答案:

答案 0 :(得分:10)

如果您正在阅读文件,最好使用BULK INSERT (Transact-SQL),如果您从内存中一次写入那么多(50K行),那么最好先写入平面文件然后在该文件上使用批量插入。

答案 1 :(得分:1)

当你正在做一个简单的插入并且没有从使用LinqToSql获得太多时,看看SqlBulkCopy,它将删除大多数往返并减少Sql Server端的开销。您将不得不进行很少的编码更改才能使用它。

另外,请查看通过索引表的列对数据进行预排序,因为当SQL-Server更新表时,这将导致更好的缓存命中。

还要考虑是否应将数据上传到未编制索引的临时临时表,然后使用单个sql语句将存储过程插入到主表中。这个可能让SqlServer在所有CPU上传播索引工作。

答案 2 :(得分:1)

您需要检查/做很多事情。

  1. 为数据库分配了多少磁盘空间?是否可以自由地完成所有插件而不会自动增加尺寸?如果没有,请增加数据库文件大小,因为它必须停止每隔这么多的插入来自动调整数据库本身的大小。

  2. 不要单独插入。他们走得太久了。而是使用表值参数(sql 2008),sql批量复制或单个插入语句(按优先顺序)。

  3. 删除该表上的所有索引,并在加载后重新创建它们。有了这么多的插入物,无论如何它们可能会被打碎。

  4. 如果您有任何触发器,请考虑将其丢弃,直到加载完成。

  5. 数据库服务器中是否有足够的可用RAM?你需要检查服务器本身,看它是否消耗所有可用的RAM?如果是这样,您可能会考虑在加载之前重新启动... sql server倾向于消耗并保持它可以获得它的所有内容。

  6. 沿着RAM线,我们希望在服务器中保留足够的RAM以将整个数据库保存在内存中。我不确定这对你是否可行。

  7. 磁盘速度如何?队列深度是否相当长?除了硬件更换之外,这里没有太多工作要做。