SQLServer优化器选择不适当的查询计划原因之一
使用复杂的SQL脚本(包含多个子查询,连接,复杂的查询条件等)做查询时,有时候会碰到SQL性能问题。
使用Set Statistics Profile on打开查询计划查看SQLServer优化器是否选择了适当的连接方式来做join,例如:如果在数据量很大的两个结果集间做连接使用了Nest Loop方式的连接则视为不适当。
如果存在上述问题,查看查询计划中连接操作所连接的两个表的EstimateRows是否和实际的结果集行数差距很大。
如果存在上述问题,使用sp_helpstats N'your_table_name', 'ALL'和DBCC SHOW_STATISTICS('your_table_name', your_statistics_name)命令查看连接操作所使用的表的统计信息是否过期,如果统计中的Rows和实际表的行数不同,则视为统计过期。
如果存在上述问题,可以:
1. 使用UPDATE STATISTICS命令更新单表的统计;
2. 使用EXEC sp_updatestats更新数据库的所有统计;
3. 使用以下脚本更新指定库的所有表:
SET NOCOUNT ON DECLARE @SQLcommand NVARCHAR(512), @Table SYSNAME DECLARE curAllTables CURSOR FOR SELECT table_schema + '.' + table_name FROM information_schema.tables WHERE TABLE_TYPE = 'BASE TABLE' OPEN curAllTables FETCH NEXT FROM curAllTables INTO @Table WHILE (@@FETCH_STATUS = 0) BEGIN PRINT N'UPDATING STATISTICS FOR TABLE: ' + @Table SET @SQLcommand = 'UPDATE STATISTICS ' + @Table + ' WITH FULLSCAN' EXEC sp_executesql @SQLcommand FETCH NEXT FROM curAllTables INTO @Table END CLOSE curAllTables DEALLOCATE curAllTables SET NOCOUNT OFF GO
备注1:
即使数据库的AUTO UPDATE STATISTICS是打开的(可在ssms的数据库属性中找到),SQLServer也不是每次更新数据时都会更新统计,具体算法如下:
SQL Server 2008 determines whether to update statistics based on changes to column modification counters (colmodctrs).
A statistics object is considered out of date in the following cases:
· If the statistics is defined on a regular table, it is out of date if:
o The table size has gone from 0 to >0 rows (test 1).
o The number of rows in the table when the statistics were gathered was 500 or less, and the colmodctr of the leading column of the statistics object has changed by more than 500 since then (test 2).
o The table had more than 500 rows when the statistics were gathered, and the colmodctr of the leading column of the statistics object has changed by more than 500 + 20% of the number of rows in the table when the statistics were gathered (test 3).
· For filtered statistics, the colmodctr is first adjusted by the selectivity of the filter before these conditions are tested. For example, for filtered statistics with predicate selecting 50% of the rows, the colmodctr is multiplied by 0.5.
· One limitation of the automatic update logic is that it tracks changes to columns in the statistics, but not changes to columns in the predicate. If there are many changes to the columns used in predicates of filtered statistics, consider using manual updates to keep up with the changes.
· If the statistics object is defined on a temporary table, it is out of date as discussed above, except that there is an additional threshold for recomputation at 6 rows, with a test otherwise identical to test 2 in the previous list.
参照:http://msdn.microsoft.com/en-us/library/dd535534.aspx
备注2:
rebuild索引不会更新所有的统计,只会更新跟索引相关的统计。