2012-05-30 86 views
1

我有一个查询需要很长时间才能执行。 我需要知道是否有任何最佳的执行方式来减少执行时间。SQL查询优化

我的查询是

SELECT  TOP (2) ID, 
        (
        SELECT  SUM(CurrentStock) AS SimilarItemQuantity 
        FROM   Inventory AS T1 
        WHERE  (Inventory.ProductName = ProductName) 
        ) 
        AS Expr1 
FROM   Inventory 

认为,为20个记录,它需要15秒。 有没有更快的方法来做到这一点。

+3

你正在使用哪些DBMS? “库存”表上有哪些索引?你看过执行计划吗? – mwigdahl

+0

是'Inventory.ProductName'索引? –

+0

它的SQLSERVER没有库存表没有索引。 – Mobin

回答

3

相关子元素是一个SQl反模式,它们几乎总是可以被连接替换并加速处理。您应该在您选择顶部X时随时添加一个order by子句,否则结果将不一致。

SELECT TOP 2 I1.ID, SUM(I2.CurrentStock) AS SimilarItemQuantity 
FROM Inventory I1 
join Inventory I2 on I1.ProductName = I2.ProductName 
GROUP BY I1.ID 
ORDER BY I1.ID 
+1

+1 - 缺少的OrderBy实际上是一个BUG - 你不知道你找回了哪个ID。它现在可能会一致并在一个月内破产。 – TomTom

0

Inventory.ProductName键列)添加一个索引,并包括CurrentStockID包括柱)列。

CREATE NONCLUSTERED INDEX [Inventory_IDX_ProductName] ON [dbo].[Inventory] 
(
    [ProductName] ASC 
) 
INCLUDE ([CurrentStock],[ID]) 
WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, SORT_IN_TEMPDB = OFF, DROP_EXISTING = OFF, ONLINE = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY] 
GO 
0

你可能会考虑通过重写此作为一个群体:

select top 2 id, sum(CurrentStock) 
from Inventory i 
group by id, ProductName 
order by 2 desc 

这是假设你希望两个ID与当前最大的股票。

通常情况下,您使用TOP进行订购。

而且,正如其他人所说,有上(ID,产品名称)的指数,将有助于:

create index idx_inventory_id_ProductName on inventory(id, ProductName) 
0

如何使用聚合窗口功能(SUM(…) OVER …)?

SELECT TOP (2) 
    ID, 
    SUM(CurrentStock) OVER (PARTITION BY ProductName) AS SimilarItemQuantity 
FROM Inventory 

正如其他人已经提到,TOP (n)没有多大意义没有ORDER BY。为了一致性,在这种情况下使用固定的顺序,例如, ORDER BY ID