我有一个数据库,在其中我将文件加载到临时表中,从该临时表中我有1-2个联接来解析一些外键,然后将这些行插入到最终表中(每月有一个分区)。我有大约34亿行用于三个月的数据。

将这些行暂存到最终表中的最快方法是什么? SSIS数据流任务(使用视图作为源并具有快速加载功能)或插入INTO SELECT ....命令?我尝试了“数据流任务”,并在5个小时内可以得到大约10亿行(8核/服务器上192 GB RAM),这对我来说感觉很慢。

评论

分区是否位于单独的文件组中(并且位于不同物理磁盘上的那些文件组中)?

一个非常好的资源,《数据加载性能指南》。这解决了许多您可以执行的性能优化,例如启用TF610,使用BCP OUT / IN,SSIS等。您只需遵循建议并在您的环境中对其进行测试。

@Aaron是的,每月有一个文件组,附加了12个San lun,因此所有jan都放在一个lun中,等等。不确定每个lun有多少磁盘,但应该足够。

是的,我的意思是“磁盘集”,也许还可以提到控制器,这些控制器可能会变得饱和。

@Kin看了一下指南,但似乎已经过时了,“ SQL Server目标是将数据从Integration Services数据流批量加载到SQL Server的最快方法。此目标支持SQL Server的所有批量加载选项– ROWS_PER_BATCH除外。”在SSIS 2012中,他们建议使用OLE DB目标以获得更好的性能。

#1 楼

一种常见方法:


在目标表上禁用/删除索引/约束。
INSERT dbo.[Target] WITH (TABLOCKX) SELECT ...
当然,有了JNK,您可以批量执行上述操作n行,这可以减少事务日志上的压力,并且当然意味着如果某个批次失败,则只需从该批次开始。我在此处发布了有关此内容的博客(引用删除时,也应用了相同的基本概念):http://www.sqlperformance.com/2013/03/io-subsystem/chunk-deletes
重新启用/重新在目标表上创建索引/约束(如果不是所有操作都不需要的话,也许可以推迟其中的一些,并且使基本数据快速联机更为重要)。

分区是物理的,而不仅仅是逻辑上的分区,通过让不同的进程同时填充不同的分区,您可能会花费一些时间(当然,这意味着您不能使用TABLOCK / TABLOCKX)。假定源还适用于多个进程的选择,而无需选择重叠/锁定等,并使操作的这一端更加缓慢(提示:在源上创建适合于目标分区方案的聚簇索引)。

您可能还会考虑一些更原始的东西,例如BCP OUT / BCP IN

我不知道我会跳到SSIS来帮助解决这个问题。那里可能有一些效率,但是我不知道这种努力可以证明节省的费用。

评论


如果您的数据未排序,请不要盲目删除索引(尤其是聚集索引)。删除索引并期望重新创建聚簇索引可能是一个巨大的错误,因为它可能会花费巨大的磁盘空间和大量的时间。我不是第一个遇到这种错误的人。查看本文sqlmag.com/t-sql/…中的“计划B”描述。作者有同样的问题。

– jyao
16-4-11在23:06



#2 楼

从SSIS的角度来看您的问题,我觉得这样做可能花了很长时间的原因是您没有进行批处理。这可能会导致SSIS管道中填充过多行,并因此而阻碍SSIS性能。您需要做的是更改每批设置的行数,并可能更改最大插入提交大小。现在,您也对此进行了设置将取决于SSIS服务器可用的内存量?您的SQL Server实例的磁盘速度是多少?最好的方法是测试。例如使用10,000。这将一次向服务器10,000发送一批,从而防止您的管道溢出,并有助于更快地运行此过程。这些设置在您的OLEDB目标中设置。



如果遇到问题,您也可以按照@AaronBertrand的建议在执行前后添加执行SQL任务,并删除/重新添加任何索引或约束。表。

评论


关于DBA.SE上其他位置需要什么“快速加载”,有一个很好的问题:dba.stackexchange.com/questions/141430/…。

–万事通
17年12月18日在22:21