基于起始日期的慢速SQL查询

基于起始日期的慢速SQL查询,sql,sql-server,database,optimization,Sql,Sql Server,Database,Optimization,下面给了我一个要运行的查询,在我创建的应用程序中,起始日期可以在运行时更改。因此,如果我运行“2010年1月1日”的开始日期,我将检索到更多返回的数据216620行,而如果我使用3天前的日期“2017年10月17日”,则返回1006行,但由于某些原因,该查询需要非常长的时间,并且在我的应用程序中超时 是否应该以某种方式优化此查询,或者这可能是服务器/硬件问题?我发现这很奇怪,过去3天的查询比查询跨越多年的数据要长得多,不幸的是,在我的WinForms应用程序中超时了 SELECT AC.acco

下面给了我一个要运行的查询,在我创建的应用程序中,起始日期可以在运行时更改。因此,如果我运行“2010年1月1日”的开始日期,我将检索到更多返回的数据216620行,而如果我使用3天前的日期“2017年10月17日”,则返回1006行,但由于某些原因,该查询需要非常长的时间,并且在我的应用程序中超时

是否应该以某种方式优化此查询,或者这可能是服务器/硬件问题?我发现这很奇怪,过去3天的查询比查询跨越多年的数据要长得多,不幸的是,在我的WinForms应用程序中超时了

SELECT AC.account_and_parents As Account, 
    TR.IBLoad as [Load ID], 
    LD.load_inboundBOL as [Customer Details],
    TR.ItemNumber as ITEMNUM, 
    IT.[Description] As[Description], 
    TR.ToPalletID As[Pallet ID],
    Format(TR.Receivedate, 'MM/dd/yyyy') as Receive_Date, 
    TR.QTY as NETWEIGHT, 
    TR.WeightGross as [Gross Weight], 
    TR.ContainerType, 
    TR.InvenType,
    TR.Route,
    tr.ToWarehouse  as Warehouse,
    tr.category as Category, 
    tr.FGatIntake as [FG at Intake],
    CASE 
    When TR.FGatIntake = 1
    THEN
        (SELECT TOP 1 tr.ItemNumber FROM [databaseName].[dbo].[Transaction] TR1 WHERE TR1.ToPalletID = TR.ToPalletID and TransCode = 'FRCPT')
    END As[Finished Good]
    FROM [databaseName].[dbo].[Transaction] TR
    INNER JOIN [databaseName].[dbo].[Item] IT 
    on tr.ItemNumber = IT.ItemNumber
    INNER JOIN som5.dbo.Loads LD 
    on TR.IBLoad = LD.OID 
    INNER JOIN [SOM5].[dbo].[Accounts] AC
    on ld.load_Account = AC.OID

             --  PROBLEM IS HERE. Lots or records (January start) are fast,
             --    but few records (October start) are *very* slow. 
    WHERE (TransDateTime Between '10/16/2017' and '10/19/2017')
    and Transcode = 'BRCPT'
    and ToPalletID not in (Select FromPalletID FROM [SOM5].[dbo].[Transaction] where TransCode = 'UNBRCPT') 
        ORDER BY Receive_Date,[Load ID],[Pallet ID]

我找到了一种使查询更快的方法,尽管我不知道为什么它能工作。
我从事务表492k+行中进行了选择,修改后的查询有问题,最后是来自该行的查询。我无法解释为什么这样做有效,但这让问题变得很快

我的最佳猜测是,原始查询没有足够快地使用Where子句筛选行

我将尝试重写查询,将主表的where子句放入子查询中。子查询应该具有优先级,返回一小部分数据;然后,这些较少的行将连接到其他表并遍历CASE语句。至于为什么可能更大的数据集执行得如此之快。。。我不确定,但我知道SQLServer缓存了以前查询的结果

SELECT AC.account_and_parents As Account, 
       TR.[Load ID], 
       LD.load_inboundBOL as [Customer Details],
       TR.ITEMNUM, 
       IT.[Description] As[Description], 
       TR.[Pallet ID],
       Format(TR.Receivedate, 'MM/dd/yyyy') as Receive_Date, 
       TR.NETWEIGHT, 
       TR.[Gross Weight], 
       TR.ContainerType, 
       TR.InvenType,
       TR.Route,
       tr.Warehouse,
       tr.category as Category, 
       tr.[FG at Intake],
       CASE 
       When TR.[FG at Intake] = 1
       THEN (SELECT TOP 1 tr.ItemNumber FROM [databaseName].[dbo].[Transaction] TR1 WHERE TR1.ToPalletID = TR.[Pallet ID] and TransCode = 'FRCPT')
    END As[Finished Good]
  FROM (
          SELECT IBLoad as [Load ID],
                 ItemNumber as ITEMNUM, 
                 ToPalletID As[Pallet ID],
                 Format(Receivedate, 'MM/dd/yyyy') as Receive_Date, 
                 QTY as NETWEIGHT, 
                 WeightGross as [Gross Weight], 
                 ContainerType, 
                 InvenType,
                 Route,
                 ToWarehouse  as Warehouse,
                 category as Category, 
                 FGatIntake as [FG at Intake]
            FROM [databaseName].[dbo].[Transaction]
           WHERE TransDateTime >= '2017-10-16'
             AND TransDateTime <= '2017-10-19'
       ) AS TR INNER JOIN [databaseName].[dbo].[Item] IT on tr.ITEMNUM = IT.ItemNumber
               INNER JOIN som5.dbo.Loads LD on TR.[Load ID] = LD.OID 
               INNER JOIN [SOM5].[dbo].[Accounts] AC on ld.load_Account = AC.OID

你有一个查询计划,我们可以看到,以确定瓶颈我编辑了我的文章,提出了查询计划。希望这能为您提供足够的信息。不确定您的事务表有多大,但两侧都有聚集索引扫描的嵌套循环可以从事务表上至少一个(如果不是两个)NCI中受益。96%的执行时间都在索引扫描上。也许更快的日期更容易访问。碎片化情况如何?磁盘上的io速度慢吗?事务表总共有492443行。没有任何IO问题或碎片问题。我在考虑使用索引视图,但从我读到的情况来看,在很少写,很多读的情况下,这会更好。但是这个表每天大约有250次写入。