代码之家  ›  专栏  ›  技术社区  ›  ninesided

T-SQL中临时表索引的最佳使用

  •  13
  • ninesided  · 技术社区  · 17 年前

    如果要在存储过程中创建临时表,并希望在其上添加一个或两个索引,以提高针对它所做的任何附加语句的性能,那么最好的方法是什么?赛巴斯说 this :

    “创建索引时,表必须包含数据。如果创建临时表并在空表上创建索引,则自适应服务器不会创建柱状图和密度等列统计信息。如果在创建索引后插入数据行,则优化器的统计信息不完整。”

    但最近一位同事提到,如果我在一个与实际使用临时表的存储过程不同的存储过程中创建临时表和索引,那么adaptive server optimiser 能够利用它们。

    总的来说,我不太喜欢只增加一点价值的包装程序,所以实际上我还没有准备好测试它,但是我想我应该把问题提出来,看看是否有人有其他的方法或建议?

    3 回复  |  直到 10 年前
        1
  •  7
  •   Community Mohan Dere    9 年前

    一些想法:

    • 如果临时表太大,必须对其进行索引,那么是否有更好的方法来解决这个问题?
    • 您可以强制它使用索引(如果您确定索引是访问表的正确方式),方法是给出形式如下的优化提示:

      SELECT * 
      FROM   #table (index idIndex) 
      WHERE  id = @id
      

    如果您对一般的性能提示感兴趣,我在这里详细地回答了一些其他问题:

        2
  •  3
  •   Eric Z Beard    17 年前

    将数据放入临时表后添加索引有什么问题?

    您需要注意的一件事是索引对可能同时运行的过程的其他实例的可见性。

    我喜欢向这些类型的临时表(和索引)添加一个guid,以确保不会发生冲突。这种方法的另一个好处是,您可以简单地使临时表成为一个真正的表。

    另外,确保您需要查询这些临时表中的数据。 不止一次 在运行存储过程的过程中,否则创建索引的成本将超过选择的好处。

        3
  •  1
  •   John M    17 年前

    在Sybase中,如果您创建一个临时表,然后在一个过程中使用它,那么选择的计划将使用表中估计的100行来构建。(该计划是在填充表之前开始该过程时生成的。)这可能导致对临时表进行表扫描,因为它只有“100行”。调用另一个过程会导致Sybase使用实际的行数为select构建计划,这允许优化器选择一个更好的索引来使用。我已经看到使用这种方法的显著改进,但是在数据库上进行测试,因为有时没有区别。