我正在编写一个存储过程,以将行插入表中。问题在于,在某些操作中,我们可能想插入超过一百万行,并且希望使其速度更快。另一件事是在其中一列中是Nvarchar(MAX)。我们可能要在此列中平均放置1000个字符。
Nvarchar(MAX)
首先,我编写了一个prc来逐行插入。然后,我生成一些随机数据以插入该NVARCHAR(MAX)列,该列为1000个字符的字符串。然后使用循环调用prc插入行。性能非常差,如果我使用SQL Server登录要插入的数据库服务器,则需要48分钟。如果我使用C#连接到台式机中的服务器(这是我们通常要执行的操作),则大约需要90分钟以上的时间。
NVARCHAR(MAX)
然后,我将prc更改为采用表类型参数作为输入。我以某种方式准备了行,并将其放入表类型参数中,并通过以下命令进行插入:
INSERT INTO tableA SELECT * from @tableTypeParameterB
我尝试将批量大小设置为1000行和3000行(将@tableTypeParameterB中的1000-3000行插入一次)。性能还是很差的。如果在SQL Server中运行一百万行,则大约需要3分钟才能插入;如果使用C#程序从桌面进行连接,则大约需要10分钟。
将tableA有2列的聚集索引。
tableA
我的目标是使插入尽可能快(我的目标是在1分钟内)。有什么方法可以对其进行优化吗?
只是一个更新:
我尝试了以下某些人建议的大容量复制插入。我尝试使用SQLBULKCOPY一次插入1000行和10000行。插入100万行的性能仍然是10分钟(每行都有一个包含1000个字符的列)。性能没有改善。还有其他建议吗?
根据评论的要求进行更新。
数据实际上来自UI。用户将更改用户界面以批量选择一百万行,并将一列从旧值更改为新值。该操作将在一个单独的过程中完成。但是,我们需要做的是使中间层服务从UI中获取旧值和新值,并将它们插入表中。旧值和新值最多可包含4000个字符,平均为1000个字符。我认为长字符串的旧值/新值会减慢速度,因为当我将测试数据的旧值/新值更改为20-50个字符并插入时非常快,无论使用SQLBulkCopy还是表类型变量
我认为,如果您更喜欢使用SQL,那么您正在寻找的是批量插入。
或者也有用于批处理操作的ADO.NET选项,因此您可以将逻辑保留在C#应用程序中。这篇文章也很完整。
更新
是的,恐怕批量插入仅适用于导入的文件(来自数据库内部)。
我有一个Java项目的经验,我们需要插入数百万行(数据来自应用程序外部)。
数据库是Oracle,因此我们当然使用了Oracle的多行插入。原来,在Java批量更新是 多 比甲骨文的多值插入(所谓的“批量更新”)更快。
如果要处理的数据来自应用程序外部(如果尚未存储在数据库中),我想说的就是去ADO.NET批处理插入。我认为这是您的情况。
注意:请记住,批处理插入通常与同一查询一起使用。 这就是它们如此之快的原因。