【问题标题】:Too Long Query Duration in SQL Server 2008 R2 DataCenterSQL Server 2008 R2 DataCenter 中的查询持续时间过长
【发布时间】:2010-12-07 14:34:36
【问题描述】:

我们有一个查询和this is an actual execution plan

如您所见 - Clustered Index Seek 占用 99%。 它还寻找主键(类型 int)。

来源有 275 000 行。
AuthorSource 有 2 275 000 行。

不使用分区和压缩。

问题是第一次执行需要 25-40 秒。但是第二次运行连续需要1-2秒。

我们还在此服务器上运行复制、队列读取器、日志读取器代理。
内存量:4GB
Sql Server 使用:3.7GB

我们认为,sql 在第一次执行后缓存查询一段时间,这就是第二次运行只需要 1-2 秒的原因。

但是不管缓存等原因,很奇怪,主键索引查找查询需要20-40秒。

重复此问题。我们为查询提供的任何不同参数 - 我们都会得到相同的结果:第一次查询很长,第二次查询速度很快。

可能是我们必须使用的一些额外设置或资源管理器能力?

        exec sp_executesql N'
SELECT [Project1].[C1] AS         [C1]
FROM   ( SELECT CAST(1 AS bit) AS X
       ) AS [SingleRowTable1]
       LEFT OUTER JOIN
              (SELECT [GroupBy1].[A1] AS                        [C1]
              FROM    ( SELECT COUNT(CAST(1 AS bit)) AS         [A1]
                      FROM    (SELECT [Extent1].[Mention_ID]                       AS [Mention_ID]                      ,
                                      [Extent1].[Theme_ID]                         AS [Theme_ID]                        ,
                                      [Extent1].[Mention_Weight]                   AS [Mention_Weight]                  ,
                                      [Extent1].[AuthorSource_ID]                  AS [AuthorSource_ID1]                ,
                                      [Extent1].[Mention_CreationDate]             AS [Mention_CreationDate]            ,
                                      [Extent1].[Mention_DeletedMark]              AS [Mention_DeletedMark]             ,
                                      [Extent1].[Mention_AuthorTags]               AS [Mention_AuthorTags]              ,
                                      [Extent1].[Mention_Tonality]                 AS [Mention_Tonality]                ,
                                      [Extent1].[Mention_Comment]                  AS [Mention_Comment]                 ,
                                      [Extent1].[Mention_AdditionDate]             AS [Mention_AdditionDate]            ,
                                      [Extent1].[UserToAnswer_ID]                  AS [UserToAnswer_ID]                 ,
                                      [Extent1].[GeoName_ID]                       AS [GeoName_ID]                      ,
                                      [Extent1].[Geo_ID]                           AS [Geo_ID]                          ,
                                      [Extent1].[Mention_PermaLinkHash]            AS [Mention_PermaLinkHash]           ,
                                      [Extent1].[Mention_IsFiltredByAuthor]        AS [Mention_IsFiltredByAuthor]       ,
                                      [Extent1].[Mention_IsFiltredByGeo]           AS [Mention_IsFiltredByGeo]          ,
                                      [Extent1].[Mention_IsFiltredBySource]        AS [Mention_IsFiltredBySource]       ,
                                      [Extent1].[Mention_IsFiltredBySourceType]    AS [Mention_IsFiltredBySourceType]   ,
                                      [Extent1].[GengineLog_InstanceId]            AS [GengineLog_InstanceId]           ,
                                      [Extent1].[Mention_PermaLinkBinaryHash]      AS [Mention_PermaLinkBinaryHash]     ,
                                      [Extent1].[Mention_APIType]                  AS [Mention_APIType]                 ,
                                      [Extent1].[Mention_IsFilteredByAuthorSource] AS [Mention_IsFilteredByAuthorSource],
                                      [Extent1].[Mention_IsFavorite]               AS [Mention_IsFavorite]              ,
                                      [Extent1].[Mention_SpamType]                 AS [Mention_SpamType]                ,
                                      [Extent1].[MentionContent_ID]                AS [MentionContent_ID]               ,
                                      [Extent2].[AuthorSource_ID]                  AS [AuthorSource_ID2]                ,
                                      [Extent2].[Author_ID]                        AS [Author_ID]                       ,
                                      [Extent2].[Source_ID]                        AS [Source_ID]                       ,
                                      [Extent2].[Author_Nick]                      AS [Author_Nick]                     ,
                                      [Extent2].[Author_UrlBinaryHash]             AS [Author_UrlBinaryHash]            ,
                                      [Extent2].[AuthorSource_Type]                AS [AuthorSource_Type]               ,
                                      [Extent2].[Author_Url]                       AS [Author_Url]                      ,
                                      [Extent2].[AuthorSource_Description]         AS [AuthorSource_Description]        ,
                                      [Extent2].[AuthorSource_Gender]              AS [AuthorSource_Gender]
                              FROM    [dbo].[Mention]                              AS [Extent1]
                                      LEFT OUTER JOIN [dbo].[AuthorSource]         AS [Extent2]
                                      ON      [Extent1].[AuthorSource_ID] = [Extent2].[AuthorSource_ID]
                              WHERE   (
                                              [Extent1].[Mention_DeletedMark] <> CAST(1 AS bit)
                                      )
                              AND
                                      (
                                              [Extent1].[Mention_IsFiltredByAuthor] <> CAST(1 AS bit)
                                      )
                              AND
                                      (
                                              [Extent1].[Mention_IsFilteredByAuthorSource] <> CAST(1 AS bit)
                                      )
                              AND
                                      (
                                              [Extent1].[Mention_IsFiltredByGeo] <> CAST(1 AS bit)
                                      )
                              AND
                                      (
                                              [Extent1].[Mention_IsFiltredBySource] <> CAST(1 AS bit)
                                      )
                              AND
                                      (
                                              [Extent1].[Mention_IsFiltredBySourceType] <> CAST(1 AS bit)
                                      )
                              )                              AS [Filter1]
                              LEFT OUTER JOIN [dbo].[Source] AS [Extent3]
                              ON      [Filter1].[Source_ID] = [Extent3].[Source_ID]
                      WHERE   (
                                      [Filter1].[Theme_ID] = @p__linq__49557
                              )
                      AND
                              (
                                      [Extent3].[Source_Type] <> @p__linq__49558
                              )
                      ) AS [GroupaBy1]
              ) AS [Project1]
       ON     1 = 1
',N'@p__linq__49557 int,@p__linq__49558 int',@p__linq__49557=7966,@p__linq__49558=8

IndexSeeking Performance Information

我们还用这个简单的代码在 sql 中手动编写查询:

        Select COUNT(1) from Mention m inner join AuthorSource auth on m.AuthorSource_ID = auth.AuthorSource_ID inner join
    Source s on auth.Source_ID = s.Source_ID where 
    m.Mention_DeletedMark = 0 AND m.Mention_IsFilteredByAuthorSource = 0 AND m.Mention_IsFiltredByAuthor = 0 
    AND m.Mention_IsFiltredByGeo = 0 AND m.Mention_IsFiltredBySource = 0 AND m.Mention_IsFiltredBySourceType = 0
    AND m.Theme_ID = 7966
    and s.Source_Type <> 8 

执行计划与我们发布的相同。

【问题讨论】:

  • 请同时发布查询。
  • 你能在不改变查询语义的情况下将所有&lt;&gt; CAST(1 AS bit) 更改为= CAST(0 AS bit) 吗?这些列可以为空吗?
  • @mmcteam.com.ua - 你正在寻找。不确定嵌套循环是否是此行数的最佳连接策略。对于您的性能观察,最可能的解释是它第一次运行时需要执行大量物理 i/o,并且在随后的执行中,页面位于缓冲区缓存中。你可以试试SET STATISTICS IO ONSET STATISTICS TIME ON吗?
  • 您可以通过查看反复使用CHECKPOINT; DBCC DROPCLEANBUFFERS 清除缓存是否会导致问题再次出现来确定。显然,最好在开发服务器上进行测试!
  • 在您发布的查询中,将两个 inner join 更改为 inner hash join 会使事情变得更好还是更糟?

标签: sql sql-server sql-server-2008


【解决方案1】:

查询很麻烦,但您似乎缺少Mention.Theme_ID 上的索引?

Sql server 出现问题,因为使用了很多&lt;&gt;,这意味着它不能使用索引,必须获取所有内容然后对其进行排序。

【讨论】:

  • 我们在 Mention.Theme_Id 上有索引(该字段位于名为 Big_Index 的索引中) - 您可以在执行计划中看到它。关于 - 你可以从执行计划中看到 99% 需要索引查找。所以sql使用索引。并且索引寻找唯一需要时间进行此查询的操作。
  • 好的,谢谢。查询执行时查看每个表的逻辑读取量会很有趣。
  • 编辑过的帖子 - 添加了带有索引搜索性能信息的图像链接。
  • 我们添加了每个表的逻辑读取量的注释
【解决方案2】:

在 cmets 中的Martin's 建议提出问题后,答案在于了解 SQL Server 如何构建执行计划并计算首次运行查询所需的磁盘读取操作。

在我们的特定情况下,强制inner hash join 而不是inner join 为我们提供我们预期的结果以及SQL 默认选择的不同执行计划。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多