SQL 服务器执行计划审核请求

SQL Server Execution Plan Review Request

无法理解为什么我的查询需要这么长时间,请寻求优化建议。

update Laserbeak_Main.dbo.ACCOUNT_MPN set
    DateUpgrade = ord.ConnectedDate
                    FROM [ORDER] ord
                    WHERE ord.AccountNumber = Laserbeak_Main.dbo.ACCOUNT_MPN.AccountNumber
                    AND ord.ordertypeID = '2'
                    AND ord.ConnectedDate IS NOT NULL
                    AND DateUpgrade <> ord.ConnectedDate

Execution plan as requested on brentozar.com

更新:根据建议,新查询看起来像这样并且似乎工作得更快。但是,如果您 运行 查询它会按预期设置行,然后 运行 它会再次更新完全相同的行数。转换为 select 确认每次都更新相同的行。 <> 子句应该阻止它,但它没有。我认为这与排序规则有关,但无法确认是否可以在同一数据库中的 table 级别使用不同的排序规则。

;WITH cteOrderInfo AS (
SELECT DISTINCT ord.AccountNumber, ord.ConnectedDate
FROM [ORDER] ord
WHERE ord.ordertypeID = '2'
AND ord.ConnectedDate IS NOT NULL
)
UPDATE Laserbeak_Main.dbo.ACCOUNT_MPN
SET Laserbeak_Main.dbo.ACCOUNT_MPN.DateUpgrade = cteOrderInfo.ConnectedDate
FROM cteOrderInfo
INNER JOIN Laserbeak_Main.dbo.ACCOUNT_MPN acc
ON cteOrderInfo.AccountNumber = acc.AccountNumber
WHERE cteOrderInfo.ConnectedDate <> acc.DateUpgrade

SELECT确认:

;WITH cteOrderInfo AS (
SELECT DISTINCT ord.AccountNumber, ord.ConnectedDate
FROM [ORDER] ord
WHERE ord.ordertypeID = '2'
AND ord.ConnectedDate IS NOT NULL
)
SELECT cteOrderInfo.ConnectedDate, acc.DateUpgrade
FROM cteOrderInfo
INNER JOIN Laserbeak_Main.dbo.ACCOUNT_MPN acc
ON cteOrderInfo.AccountNumber = acc.AccountNumber
WHERE cteOrderInfo.ConnectedDate <> acc.DateUpgrade

SELECT 结果样本:

正如 Serge 所建议的,我们没有唯一的行。

我们得出的解决方案:

;WITH cteSourceStuff AS (
      SELECT AccountNumber, MpnUpgrade, MAX(DateConnected) maxConnDate
      FROM ORDER_DETAIL, [ORDER]
      WHERE ORDER_DETAIL.OrderID = [ORDER].OrderID
      AND LEN(MpnUpgrade) > 10
      AND OrderTypeID = 2
      GROUP BY AccountNumber, MpnUpgrade
      )
      UPDATE Laserbeak_Main.dbo.ACCOUNT_MPN set
              DateUpgrade = cteSourceStuff.maxConnDate
              FROM cteSourceStuff
              WHERE cteSourceStuff.MpnUpgrade = ACCOUNT_MPN.Mpn
              AND cteSourceStuff.AccountNumber = ACCOUNT_MPN.AccountNumber
              AND DateUpgrade <> cteSourceStuff.maxConnDate

这是可行的,因为最初删除了重复项,然后我们只更新我们实际定位的行。我们之前遇到问题的原因是 SQL 正在更新它找到的第一行,然后当我们 re-ran 或 运行 时 select 它是 return 匹配的行在钥匙上,但以前没有更新过。