sqlcmd 慢于 SQL Server 2008 R2

syn*_*-dj 7 sql-server-2008 insert

我正在尝试导入一个较长的 SQL 脚本(350 万行,大小为 1.5 GB),其中主要包含使用数据的短 INSERT INTO 语句,sqlcmd -E -d <database> -S 127.0.0.1 -i <scriptfile>并且它几乎爬行到停止(大约每秒 150 行)而没有推断出任何明显的SQL 服务器主机上的负载(所有 CPU 内核几乎空闲,磁盘吞吐量约为 200 KB/s)。

由于源文件位于 NFS 共享上,我首先怀疑这是罪魁祸首,但本地可用的相同脚本以相同的速度运行。

数据库基本上是空的,表是由完全相同的脚本创建的,没有触发器或其他花哨的东西——只是原始的,主要是数字或 varchar 数据。

SQLCMD 在等什么?有什么办法可以加快速度吗?

编辑:

我们在更改 SQL 脚本文件中的数据方面的手段有限。数据由第三方为进口程序提供。我相信它最初是使用 Management Studio 2005 的“Script table as...”功能导出的。

由于文件庞大,编辑文件很乏味——使用普通文本编辑器,任何操作都会花费很长时间,尽管通过将两个文件复制到一起来完成“SET NOCOUNT ON”的准备——并且它带来了大约 50% 的加速。

由于文本编码 (Unicode-LE),在不转换的情况下无法使用通用的 GNU textutils 集进行编辑(否则它可以很好地处理大文件) - 而且我不愿意转换,因为数据保真度问题可能会来吧。

因此,我对如何应用有关插入 BEGIN TRAN/COMMIT TRAN 块或将单个插入项转换为更大集合的建议有些困惑。

Aar*_*and 12

一些想法:

  • GO每千行或几千行注入一些命令。然后,它不是一个巨大的批次,而是分成多个批次。
  • 将您的个人INSERT陈述更改为每个陈述INSERT ... VALUES ()一千组。
  • 无偿使用事务和提交和/或检查点(同样,每 1000 次左右插入可能是一个不错的起点,结合GO)。您的手表和日志会感谢您。
  • 这是一个愚蠢的琐碎小事,但请确保您的脚本具有SET NOCOUNT ON- 否则 UI、SQL Server 和介于两者之间的网络会花费大量时间1 row(s) affected为每个插入来回发送消息。
  • 最好的方法可能是使用BULK INSERTBCP甚至SSIS而不是 Management Studio。部分问题可能是您自己机器上的内存开销只是加载了那个巨大的文件,别介意尝试解析/执行它。我很想在这期间看到 ssms.exe 的私有字节......
  • 根据与 OP 的离线讨论,添加另一个选项:要求供应商提供备份而不是脚本。然后您可以将其恢复到某个测试或虚拟系统,并从中手动生成插入(或使用导入/导出,或 Red Gate 的数据比较工具)。这可能最终是净相同的时间,但不会用数百万个插入的巨大脚本杀死日志......

  • 我*不*应该使用 350 万个单独的单行文本文件? (2认同)