推荐的批量大小是SqlBulkCopy
多少?我正在寻找一个通用公式,可以用作性能调整的起点。
Answers:
我有一个导入实用程序与SQL Server实例位于同一台物理服务器上。使用自定义IDataReader
格式,它解析平面文件并使用SQLBulkCopy
。一个典型的文件具有约600万个合格行,平均5列十进制和短文本,每行约30个字节。
在这种情况下,我发现5,000个批处理大小是速度和内存消耗的最佳折衷方案。我从500开始,然后尝试更大的尺寸。我发现5000的平均速度是500的2.5倍。插入600万行的批量大小为5,000大约需要30秒,批量大小为500大约需要80秒。
10,000并没有明显提高。增加到50,000可以使速度提高几个百分点,但是增加服务器的负载是不值得的。超过50,000的速度没有改善。
这不是一个公式,但它是供您使用的另一个数据点。
我也花了一些时间研究这个问题。我正在寻找使用C#控制台应用程序(.Net 2.0)优化将大型CSV文件(16+ GB,65 +百万条记录,并不断增长)导入SQL Server 2005数据库的方法。正如杰里米也已经指出的那样,你需要做一些微调您的具体情况,但我会建议你有500的首批大小,上面和下面这个测试值。
我从此MSDN论坛帖子中得到了建议,以批处理大小测试介于100到1000之间的值,对此表示怀疑。但是,当我测试100至10,000之间的批量大小时,我发现500是我的应用程序的最佳值。对于500的值SqlBulkCopy.BatchSize
还建议在这里。
要进一步优化SqlBulkCopy操作,请查看此MSDN建议;我发现使用SqlBulkCopyOptions.TableLock有助于减少加载时间。
正如其他人所说,这取决于您的环境,尤其是行数和网络延迟。
就个人而言,我将从将BatchSize
属性设置为1000行开始,然后看看其性能如何。如果可行,那么我将使行数加倍(例如增加到2000、4000等),直到超时。
否则,如果超时发生在1000,那么我将行数减少一半(例如500),直到它起作用为止。
在每种情况下,我都会尝试将最后两个尝试的批量大小之间的差值加倍(如果成功)或减半(如果失败),直到找到最佳位置。
另外要考虑的因素是它需要多长时间来复制一个单一的一批行。如果要复制的行批次超过BulkCopyTimeout
属性(默认值为30秒),则会发生超时。您可以尝试将该BulkCopyTimeout
属性加倍至60秒。这允许更长的时间段来复制较大的批处理行集。例如,一批50,000行可能只需要花费30秒左右的时间,即超过30秒的时间限制,因此将其增加到60秒可能对性能有所帮助。