2011-09-27 89 views
0

下面有一個簡單的SQL語句JOIN爲什麼這個SQL查詢需要8個小時才能完成?

SELECT  
    REC.[BarCode] 
    ,REC.[PASSEDPROCESS] 
    ,REC.[PASSEDNODE] 
    ,REC.[ENABLE] 
    ,REC.[ScanTime] 
    ,REC.[ID] 
    ,REC.[Se_Scanner] 
    ,REC.[UserCode] 
    ,REC.[aufnr] 
    ,REC.[dispatcher] 
    ,REC.[matnr] 
    ,REC.[unitcount] 
    ,REC.[maktx] 
    ,REC.[color] 
    ,REC.[machinecode] 
    ,P.PR_NAME 
    ,N.NO_NAME 
    ,I.[inventoryID] 
    ,I.[status] 
    FROM tbBCScanRec as REC 
     left join TB_R_INVENTORY_BARCODE as R 
     ON REC.[BarCode] = R.[barcode] 
      AND REC.[PASSEDPROCESS] = R.[process] 
      AND REC.[PASSEDNODE] = R.[node] 
     left join TB_INVENTORY as I 
     ON R.[inventid] = I.[id] 
     INNER JOIN TB_NODE as N 
     ON N.NO_ID = REC.PASSEDNODE 
     INNER JOIN TB_PROCESS as P 
     ON P.PR_CODE = REC.PASSEDPROCESS 

tbBCScanRec有556553條記錄,而表TB_R_INVENTORY_BARCODE有260513個reccords和表TB_INVENTORY有7688.不過,最後兩個表(TB_NODETB_PROCESS)都少於30個記錄。令人難以置信的是,它在SQL Server 2005中運行時,需要8小時才能返回結果集。

爲什麼需要很長時間來執行?

如果兩個inner join被刪除,則只需十秒鐘即可完成運行。

這是怎麼回事?

有至少兩個UNIQUE NONCLUSTERED INDEX es。

一個是IX_INVENTORY_BARCODE_PROCESS_NODE在桌子上TB_R_INVENTORY_BARCODE,其覆蓋四列(inventidbarcodeprocess,和node)。

另一種是IX_BARCODE_PROCESS_NODE在桌子上tbBCScanRec,它覆蓋三列(BarCodePASSEDPROCESS,和PASSEDNODE)。

+4

我不能推薦任何具體的教程,但你需要學習理解執行計劃。在SSMS中有一些選項可以打開執行計劃 - 如果你可以補充一下,我們可能會給你一些指示(儘管發佈一個XML查詢計劃,儘管如此)。此外,通常使用實際值而不是預計值計劃更好,但如果預計需要8小時才能獲得實際值,則預計計劃可能已足夠。 –

回答

2

好了,標準答案,這樣的問題:

  1. 確保您擁有所有必要的指標來代替,即指標上N.NO_IDREC.PASSEDNODEP.PR_CODEREC.PASSEDPROCESS
  2. 確保類型你加入的列是相同的,所以不需要隱式轉換。
+0

有至少TOW獨特的非結論性指數 – WangHu

+0

感謝您的建議.. – WangHu

1

您正在使用(556553 * 30 * 30)500百萬行左右。 您可能必須在桌上添加indexes

如果您正在使用SQL Server,則可以觀看計劃查詢以查看您在哪裏丟失時間。 請參閱此處的文檔:http://msdn.microsoft.com/en-us/library/ms190623(v=sql.90).aspx

查詢計劃將幫助您創建索引。

+0

我不按照您估計的5億行。你可以解釋嗎? –

+0

加工過程中處理**的估計最大行數**是笛卡爾乘積。這是每個表格行數的乘積:「最差」情況... –

+0

好吧,那麼是不是在談論結果集的大小?那麼你在計算中錯過了兩張表,不是嗎? 'TB_R_INVENTORY_BARCODE'具有260513行和'TB_INVENTORY'具有7688行 –

相關問題