为什么AND SQL on SQL update语句运行缓慢?

时间:2017-09-21 10:05:24

标签: c# sql-server

CREATE TABLE [LB].[Orders]
(
    [OrderID] [bigint] IDENTITY(1,1) NOT NULL,
    [OrderDate] [date] NOT NULL,
    [Status] [nvarchar](max) NULL,

    CONSTRAINT [PK_MasterOrderID] 
        PRIMARY KEY CLUSTERED ([OrderID] ASC)
) 

CREATE NONCLUSTERED INDEX [PK_Index]  
    ON [BTP_NYA].[LB].[Orders] ([OrderDate]); 

为什么更新#1比更新#2快得多?

string newStaus = "Message";
long OrderID = 123;

// Update #1:
UPDATE [BTP_NYA].[XX].[Orders] 
SET [Status] = '" + newStatus + "' 
WHERE [OrderID] = " + orderID.ToString("0") + "";

// Update #2:
UPDATE [BTP_NYA].[XX].[Orders] 
SET [Status] = '" + newStatus + "' 
WHERE [OrderID] = " + orderID.ToString("0") + " 
  AND [Status] = 'NEW'

更新#1需要0-1毫秒,更新#2需要7-8毫秒

唯一的区别是我在更新#2中检查Status == 'NEW'。我无法将状态编入索引,因为它会频繁更改值。

1 个答案:

答案 0 :(得分:1)

  

为什么此更新1比Update 2快得多

更新一个人正在使用它的主键 WHERE [OrderID] =来查询表格。这本质上是O(log n)的二叉树搜索复杂度(n是表中记录的数量)

更新二是按主键和另一列

进行搜索
WHERE [OrderID] = " + orderID.ToString("0") + " AND [Status] = 'NEW'

现在可以使用二叉树来获取与订单ID匹配的值(仍为O(log n)),但它必须遍历所有这些记录,以查看哪些匹配[Status] "NEW" 。我不是100%肯定SQL将如何优化它,我认为它仍将使用二叉树匹配然后迭代这些结果,因此复杂性如下:

O((x=(log n)) * x)

更高的复杂性=找到记录的时间更长。

但这会稍微改变,具体取决于SQL认为是优化此查询的最有效方式。如果您包含执行计划,您将能够看到这一点。

参考:

Big O cheat cheeet