Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sql-server/23.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
SQL Server函数间歇性性能问题_Sql_Sql Server_Sql Server 2008_Sql Function - Fatal编程技术网

SQL Server函数间歇性性能问题

SQL Server函数间歇性性能问题,sql,sql-server,sql-server-2008,sql-function,Sql,Sql Server,Sql Server 2008,Sql Function,我们的数据库中有一个函数,它搜索两个大表以查看值是否存在。这是一个相当大的查询,但它经过优化以使用索引,并且通常运行得相当快 在过去的两周内,这个函数有三次决定失控,运行速度非常慢,这会导致死锁和糟糕的性能。即使在使用量低于峰值时也会发生这种情况 在SQLServer中使用“alterfunction”重建函数似乎可以解决这个问题。一旦我们这样做了,服务器的使用就会恢复正常,一切正常 这使我们认为函数查询计划已经重建,并且考虑了正确的索引,但是我们不知道为什么SQL Server突然决定将查询计

我们的数据库中有一个函数,它搜索两个大表以查看值是否存在。这是一个相当大的查询,但它经过优化以使用索引,并且通常运行得相当快

在过去的两周内,这个函数有三次决定失控,运行速度非常慢,这会导致死锁和糟糕的性能。即使在使用量低于峰值时也会发生这种情况

在SQLServer中使用“alterfunction”重建函数似乎可以解决这个问题。一旦我们这样做了,服务器的使用就会恢复正常,一切正常

这使我们认为函数查询计划已经重建,并且考虑了正确的索引,但是我们不知道为什么SQL Server突然决定将查询计划更改为更糟糕的计划


有没有人知道是什么导致了这种行为,或者如何测试或预防这种行为?我们正在运行SQL Server 2008 Enterprise。

您所描述的行为通常是由于缓存的查询计划不正确和/或统计数据过时所致

当WHERE子句中有大量参数时,尤其是一长串参数时,通常会出现这种情况:

(@parameter1 is NULL OR TableColumn1 = @parameter1)
比方说,缓存的查询计划过期,并使用一组不具有代表性的参数调用proc。然后为该数据配置文件缓存该计划。但是,如果proc更常见,参数集非常不同,那么该计划可能不合适。这通常被称为“参数嗅探”

有一些方法可以缓解和消除此问题,但它们可能涉及权衡,并取决于您的SQL Server版本。看和看。如果(这是一个很大的如果)进程很少被调用,但必须以尽可能快的速度运行,您可以将其标记为,以便在每次调用它时强制重新编译,但不要对频繁调用的进程或在没有调查的情况下执行此操作

[注意:请注意您的SQL Server 2008框中有哪些,因为在某些版本中,重新编译和参数嗅探逻辑的工作方式不同]

运行此查询(来自Glenn Berry)以确定统计信息的状态:

-- When were Statistics last updated on all indexes?
SELECT o.name, i.name AS [Index Name],  
      STATS_DATE(i.[object_id], i.index_id) AS [Statistics Date], 
      s.auto_created, s.no_recompute, s.user_created, st.row_count
FROM sys.objects AS o WITH (NOLOCK)
INNER JOIN sys.indexes AS i WITH (NOLOCK)
ON o.[object_id] = i.[object_id]
INNER JOIN sys.stats AS s WITH (NOLOCK)
ON i.[object_id] = s.[object_id] 
AND i.index_id = s.stats_id
INNER JOIN sys.dm_db_partition_stats AS st WITH (NOLOCK)
ON o.[object_id] = st.[object_id]
AND i.[index_id] = st.[index_id]
WHERE o.[type] = 'U'
ORDER BY STATS_DATE(i.[object_id], i.index_id) ASC OPTION (RECOMPILE); 

您所描述的行为通常是由于缓存的查询计划不正确和/或统计数据过时造成的

当WHERE子句中有大量参数时,尤其是一长串参数时,通常会出现这种情况:

(@parameter1 is NULL OR TableColumn1 = @parameter1)
比方说,缓存的查询计划过期,并使用一组不具有代表性的参数调用proc。然后为该数据配置文件缓存该计划。但是,如果proc更常见,参数集非常不同,那么该计划可能不合适。这通常被称为“参数嗅探”

有一些方法可以缓解和消除此问题,但它们可能涉及权衡,并取决于您的SQL Server版本。看和看。如果(这是一个很大的如果)进程很少被调用,但必须以尽可能快的速度运行,您可以将其标记为,以便在每次调用它时强制重新编译,但不要对频繁调用的进程或在没有调查的情况下执行此操作

[注意:请注意您的SQL Server 2008框中有哪些,因为在某些版本中,重新编译和参数嗅探逻辑的工作方式不同]

运行此查询(来自Glenn Berry)以确定统计信息的状态:

-- When were Statistics last updated on all indexes?
SELECT o.name, i.name AS [Index Name],  
      STATS_DATE(i.[object_id], i.index_id) AS [Statistics Date], 
      s.auto_created, s.no_recompute, s.user_created, st.row_count
FROM sys.objects AS o WITH (NOLOCK)
INNER JOIN sys.indexes AS i WITH (NOLOCK)
ON o.[object_id] = i.[object_id]
INNER JOIN sys.stats AS s WITH (NOLOCK)
ON i.[object_id] = s.[object_id] 
AND i.index_id = s.stats_id
INNER JOIN sys.dm_db_partition_stats AS st WITH (NOLOCK)
ON o.[object_id] = st.[object_id]
AND i.[index_id] = st.[index_id]
WHERE o.[type] = 'U'
ORDER BY STATS_DATE(i.[object_id], i.index_id) ASC OPTION (RECOMPILE); 

我们可能需要更多的信息。它是什么类型的函数(标量函数、表值函数或内联函数)?它操作的表的结构是什么?有哪些索引可用,您希望它使用哪些索引?当它开始表现不好时,它到底做了什么?我们可能需要更多的信息。它是什么类型的函数(标量函数、表值函数或内联函数)?它操作的表的结构是什么?有哪些索引可用,您希望它使用哪些索引?当它开始表现不好时,它到底做了什么?我同意这听起来像参数嗅探。过时的统计数据似乎不符合事实,但是,如果统计数据不好,那么通过
Alter函数重新编译计划将无法解决问题。如果统计数据有偏差(比如在加载大数据之后),则可能会选择不正确的计划。但这更可能是由于参数嗅探,我同意这听起来像参数嗅探。过时的统计数据似乎不符合事实,但是,如果统计数据不好,那么通过
Alter函数重新编译计划将无法解决问题。如果统计数据有偏差(比如在加载大数据之后),则可能会选择不正确的计划。但更可能的原因是参数嗅探