【问题标题】:Drop/Rebuild indexes during Bulk Insert批量插入期间删除/重建索引
【发布时间】:2011-10-20 19:00:33
【问题描述】:

我的表中有超过 7000 万条记录;我刚刚发现开发人员在批量插入之前删除索引,然后在批量插入结束后再次创建。存储过程的执行时间接近 30 分钟(删除索引,批量插入,然后从头开始重新创建索引

建议:从拥有超过 70 多万条记录且每天增加 3-4 百万条记录的表中删除 INDEX 是否是一种好习惯。

在批量插入之前不删除索引是否有助于提高性能?

在 BIG TABLE 中进行 BULK 插入时应遵循的最佳做法是什么。

感谢和问候

【问题讨论】:

  • 你试过了吗?装载期间是否正在使用桌子?你使用临时表吗?
  • 我会担心为什么你每天加载 7000 万个现有行,而实际上只有 3-400 万行是新的。
  • @KM:我认为 3-4 是现有 70 的负载。这也意味着到目前为止可能还有 20 天的增长......
  • @gbn,再次阅读后,似乎是这样。 Op 确实需要提供更多信息,没有“一种”方法可以做到,这取决于很多因素。

标签: sql sql-server-2005


【解决方案1】:

就像 SQL Server 中的所有内容一样,“视情况而定”

在插入期间维护索引存在开销,并且在插入之后重建索引存在开销。确定哪种方法产生较少开销的唯一方法是同时尝试它们并对其进行基准测试。

如果我是一个赌徒,我会打赌,保留索引会在完全重建中脱颖而出,但我没有全面的了解来做出有根据的猜测。同样,唯一确定的方法是尝试这两种选择。

一个关键的优化是确保您的批量插入是在集群键顺序。


如果我正确阅读了您的问题,则该表在加载期间几乎不受限制(锁定),这是一个问题。

如果您的主要目标是提高可用性/减少阻塞,请尝试采用 A/B 表方法。

A/B 方法分解如下:

给定一个名为“MyTable”的表,您实际上将有两个物理表(MyTable_A 和 MyTable_B)和一个视图(MyTable)。

如果 MyTable_A 包含当前“活动”数据集,则您的视图 (MyTable) 正在从 MyTable_A 中选择所有列。同时,您可以对 MyTable_B 进行全权委托(其中包含 MyTable_A 数据的副本和您正在编写的新数据。)一旦 MyTable_B 被加载、索引并准备就绪,更新您的“MyTable”视图以指向 MyTable_B 并截断 MyTable_A .

此方法假定您愿意增加 I/O 和存储成本(在您的情况下是显着的)以保持可用性。它还假设您的大表也是相对静态的。如果您确实遵循这种方法,我会推荐第二个视图,例如指向非实时表的 MyTable_old(即,如果 MyTable_A 是当前演示表并被 MyTable 视图引用,MyTable_old 将引用 MyTable_B)您将更新MyTable_old 视图在您更新 MyTable 视图的同时。


根据您插入的数据的性质(以及您的 SQL Server 版本/版本),您还可以利用分区 (MSDN blog on this topic.)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-10-22
    • 1970-01-01
    • 1970-01-01
    • 2011-04-30
    • 2013-10-11
    • 1970-01-01
    • 2013-08-18
    • 1970-01-01
    相关资源
    最近更新 更多