最近我们遇到了一些性能问题,因此我一直在密切监视我们的事件。我一直在运行AskBrent脚本,并获得报告“有人运行DBCC FREEPROCCACHE”,因为计划缓存还很小。我进一步使用dm_exec_query_stats进行研究,我看到计划高速缓存每隔几秒钟就会频繁清空一次。我已经在服务器上运行了跟踪,并且在同一时期内没有任何DBCC命令在运行。

有人知道还有什么可能导致计划缓存如此频繁地清空吗?

该数据库支持大量生产中的繁忙网站。在我们的登台环境(运行相同的代码)中,计划缓存已经存在了几天。在我们的开发环境中,缓存的使用时间为几分钟或几小时,这并不奇怪。我们正在群集中运行SQL Server 2008 R2 Standard。

最佳答案

@Raspin:一种可能是服务器受到内存限制,并且有许多“不同的” SQL计划(未参数化或无法自动参数化的查询执行)。

可能是因为有太多"new"计划,而SQL Server正在刷新“旧”计划。 (除了DBCC FREEPROCCACHE之外,还有其他操作会导致计划被刷新。如果存在内存压力,则未被重用的Adhoc计划将是从缓存中逐出的第一个计划。)

我建议此Microsoft白皮书进行相关讨论:

http://technet.microsoft.com/en-us/library/ee343986(v=sql.100).aspx

我不确定“集群”如何影响计划缓存。我相信每个SQL Server实例都有其自己的计划缓存。

白皮书的附录A 中的白皮书末尾列出了无法“自动参数化”的语句。

我的猜测(只是一个猜测)是“不同的” SQL语句的数量使计划缓存不堪重负。我敢冒险说,很多语句都不会被重复使用。

在我的服务器上,我将使用dm_exec_cached_plans在短时间内收集缓存中的计划的一些快照[http://technet.microsoft.com/en-us/library/ms187404(v=sql.105).aspx],然后比较快照。

条目的数量是否保持相对恒定,缓存是否已满或是否确实在某个时候被“清除”了。计划缓存中的任何语句是否都可以重用? (我认为输出中包含一个“usecounts”列,该列指示正在重新执行一条语句。)

我还将收集在短时间间隔内执行的SQL语句的痕迹,并进行回顾。大多数语句是参数化的还是自动参数化的?还是大多数都是单字单字。

SELECT *
  FROM sys.dm_exec_cached_plans
 WHERE cacheobjtype = 'Compiled Plan'
 ORDER BY objtype

大多数计划都是objtype ='Adhoc'吗?如果不重用这些计划,则在存在内存压力时最有可能将其驱逐出局。

性能问题是真的从缓存中“清除了”计划,还是其他问题,例如庞大的SQL语句,SQL语句本身的性能,对锁,闩锁,可用缓冲区的争用,等等。

关于sql-server - 是什么清除我的SQL Server计划缓存?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/23295852/

10-13 07:40