有些查询天生就消耗大量资源。这与基本的数据库和索引问题有关。这些查询的效率并不低,因为查询优化器会以最有效的可能方式实现这些查询。然而,它们确实消耗大量资源,而且 transact-sql 面向集合的性质使这些查询看起来效率很低。查询优化器的智能水平无法消除这些构造的固有资源成本。与不复杂的查询相比,这些查询的固有成本十分昂贵。虽然 microsoft(r) sql server? 2000 使用最佳的访问计划,但受到基础构造可能性的限制。
例如,下列类型的查询可能占用大量资源:
返回大结果集的查询
高度不唯一的 where 子句
不过有一些针对优化查询和提高查询性能的建议,其中包括:
添加更多的内存(尤其是如果服务器运行许多复杂查询而且其中几个查询执行很慢)。
在有多个处理器的计算机上运行 sql server。多个处理器使 sql server 得以利用并行查询。有关更多信息,请参见并行查询处理。
考虑重新编写查询。
如果查询使用游标,则确定如果使用效率更高的游标类型(如快速只进游标)或单纯查询能否更有效地编写游标查询。单纯查询的性能一般优于游标操作。一组游标语句通常是一个外循环操作,在此操作中,一旦使用内部语句便开始处理外循环内的每行,因此可考虑使用 group by 或 case 语句或改为使用子查询。
如果应用程序使用循环,可考虑在查询内放入循环。应用程序常包含带参数化查询的循环,该循环执行许多次并要求运行应用程序的计算机与 sql server 之间有网络往返。可改为使用临时表创建一个更复杂的查询。只需提供一个网络往返,查询优化器即会更好地优化这个查询。
不要对同一查询内的单个表使用多个别名以模拟索引交叉。模拟索引交叉已没有必要,因为 sql server 会自动考虑索引交叉并且可以在同一查询内的相同表上使用多个索引。例如,给出下列示例查询:
select * from lineitem
where partkey between 17000 and 17100 and
shipdate between ’1/1/1994’ and ’1/31/1994"
sql server 可以在 partkey 和 shipdate 列上都使用索引,然后在两个子集之间执行哈希匹配以获得索引交叉。
只在必要时才使用查询提示。若查询使用在 sql server 早期版本上执行的提示,则应在不指定提示的情况下对该查询进行测试。提示会防碍查询优化器选择更好的执行计划。有关更多信息,请参见 select。
利用 query governor 配置选项和设置。可以使用 query governor 配置选项阻止执行长时间运行的查询,从而防止消耗系统资源。默认情况下,query governor 配置选项允许执行所有查询,而不考虑查询所需的时间。然而,可以将查询调控器设置到最大秒数,以允许执行所有连接的所有查询或只允许执行特定连接的查询。查询调控器基于估计的查询成本而不是实际的已用时间,因此没有任何运行时开销。它还在长时间运行的查询开始前便将其停止,而不是先运行这些查询直到达到某些预定义的限制为止。有关更多信息,请参见 query governor cost limit 选项和 set query_governor_cost_limit。
新闻热点
疑难解答