如何加快对 SQL 服务器的多行插入?

Posted

技术标签:

【中文标题】如何加快对 SQL 服务器的多行插入?【英文标题】:How can I speed up multi-row inserts to SQL server? 【发布时间】:2010-09-29 21:06:10 【问题描述】:

我一次向表中插入大约 400 行(SQL Server 2008)。我已经尝试过 UNION ALL,但这大大减慢了速度。我确定了以下查询:

INSERT INTO table VALUES (a, b,...),(c, d,...),...(x,y,...); 

当我通过 ODBC 进行此查询时,大约需要 400 毫秒(我使用 C++ 并且对 sqlExecDirect 的单次调用会转到 odbc32.dll)。但是,当我在由 Getdate() 包装的 MS SQL Server Management Studio 中运行查询时:

SELECT Getdate()
INSERT INTO ...
SELECT Getdate()

大约需要 10 毫秒。作为比较,在同一台机器上,mysql 中的相同查询大约需要 20ms。

    SELECT Getdata() 是一种可靠的事务计时方法吗? 为什么 MS SQL Server Management Studio 这么快? 我可以做些什么来提高性能? ODBC的任何替代品?直接连接到 SQL 服务器?

【问题讨论】:

SSMS 查询看起来那么快的原因是因为我多次发送完全相同的查询。只需在原查询中更改一个字母,再次运行'SQL Server parse and compile',执行速度下降到非常接近ODBC的速度。 【参考方案1】:

第一次连接通常需要一段时间才能建立。这可以解释初始延迟:在 SSMS 中,当您开始查询时,连接已经到位。尝试在同一个 C++ 程序中执行两次插入操作,看看是否会有所不同。

另外:您使用的是什么 ODBC 驱动程序?对于 ODBC,请考虑本机驱动程序:

Driver=SQL Server Native Client 10.0;Server=myServerAddress;
    Database=myDataBase;Uid=myUsername;Pwd=myPassword;

除了 ODBC,您还可以通过 COM 使用 ADO。使用生成的包装器很容易做到这一点。然后您可以使用 OLE DB 进行连接:

Provider=SQLNCLI10;Server=myServerAddress;
    Database=myDataBase;Uid=myUsername; Pwd=myPassword;

【讨论】:

将驱动程序更改为SQL Server Native Client 10.0 并没有影响性能。似乎所有时间都花在“SQL Server 解析和编译时间”上,我认为这是发生的操作在服务器上。我不确定 SQL 服务器在做什么,但是花费 400 毫秒来解析和编译 40kb 的文本似乎太长了。【参考方案2】:

按照您进行基准测试的方式,您没有捕获编译时间。这样做:

SET STATISTICS TIME ON
GO
INSERT INTO ...

【讨论】:

以上是关于如何加快对 SQL 服务器的多行插入?的主要内容,如果未能解决你的问题,请参考以下文章

使用 JdbcTemplate 插入多行

如何在插入之前加快重复检查?

如何在 SQL Server CE 数据库中插入多行? [关闭]

SQL加快插入的性能?

如何将动态sql的多行结果插入另一个表?

如何在 SQL Server 中插入多行?