2

文本列的性能有一個SQL工會與工會3所有查詢的所有查詢。在查詢中添加了文本列CAST(c.getQuestionId AS VARCHAR(300))後,查詢執行時間發生了顯着變化。正在使用的數據庫是SQL SERVER 2014.性能調優專家,請幫助。如何提高在下文提到的SQL查詢

上有JcccustomersAssessmentProxy創造3項指標。這是一張擁有8000萬條記錄的表格。顯式索引的使用只在第三查詢中只提到了 (即(NOLOCK, INDEX=IX_AssessmentProxy_myJcAssessmentContext))

有上myJcAssessmentContext

一個非聚集索引

有上getmycoordtoyplanver一個非聚集索引

有一種getMyEventItem上的非聚簇索引

SELECT  ass.P_KEY 
      ,ass.SS_CODE 
      ,CAST(evp.EVENT_SSID AS VARCHAR(11)) AS EVENT_SSID 
      ,CAST(QUESTIONNUMBER AS VARCHAR(3))        AS EVENT_NO 
      ,CAST(ISNULL(CAST(TEMPLATEVERSION AS VARCHAR), 0) AS INT)  AS TEMPLATEVERSION 
      ,ISNULL(CAST(TEMPLATENAME AS VARCHAR(50)), ' ')     AS TEMPLATENAME 
      ,evp.ASS_DATE 
      ,ISNULL(ANSWERNUMBER, 0)          AS ANSWER_NO 
      ,ass.CASE_SSID 
      ,ass.RE_SSID 
      ,ass.RE_DATE 
      ,ass.EPISODE_SSID 
      ,ass.[SERVICE] 
      ,ass.SERVICE_DESC 
      ,ass.TAM_KEY 
      ,ass.PRv_KEY 
      ,CAST(QUESTIONNUMBER AS VARCHAR(3))     AS QUESTION_NO 
      ,ISNULL(CONVERT(VARCHAR(100), REPLACE(REPLACE(CAST(QUESTIONTEXT AS VARCHAR(650)), char(10), ''), char(13), ' ')), ' ') AS QUESTION_TEXT 
      ,ISNULL(CAST(ANSWER AS VARCHAR(125)), ' ')   AS ANSWER_TEXT 
      ,a.MyAssessment          AS ASSESSMENT_SSID 
----------------------------------------------------------------------------------------- 

      ,CAST(RIGHT(a.getMyCoordtoyPlanVer, 10) AS INT)  AS toy_PLAN_VERSION_SSID  
      ,CAST(RIGHT(a.myJcAssessmentContext, 10) AS INT)  AS CONTEXT_FORM_SSID 
-----------------------------------------------------------------------------------------   
      ,ass.RECORD_DATE 
           **,CAST(a.getQuestionId AS VARCHAR(300))     AS QUESTION_ID /*NEW Text Column ,this remove the parallelism*/** 
FROM  SourceFeed.dbo.JcccustomersAssessmentProxy AS a WITH(NOLOCK) 
      INNER JOIN 
      TEMP_DATABASE.dbo.jsystemReport_AllEventItems_AllPersons evp WITH(NOLOCK) 
      ON a.getMyEventItem = evp.oid 


      INNER JOIN 
      TEMP_DATABASE.dbo.jsystemAssessment      ass WITH(NOLOCK) 
      ON evp.getcustomersId = ass.customersID 
      AND evp.EVENT_SSID = ass.EVENTID 


UNION ALL 

SELECT  ass.P_KEY 
      ,ass.SS_CODE 
      ,CAST(csp.ENT_SSID AS VARCHAR(11)) AS EVENT_SSID 
      ,CAST(jcc.QUESTIONNUMBER AS VARCHAR(3)) AS EVENT_NO 
      ,CAST(ISNULL(CAST(CAST(jcc.TEMPLATEVERSION AS VARCHAR) AS VARCHAR), 0) AS INT) AS TEMPLATEVERSION 
      ,ISNULL(CAST(jcc.TEMPLATENAME AS VARCHAR(50)), ' ') AS TEMPLATENAME 
      ,csp.ASSESSMENT_DATE 
      ,ISNULL(jcc.ANSWERNUMBER, 0) AS ANSWER_NO 
      ,ass.CASE_SSID 
      ,ass.REF_SSID 
      ,ass.RE_DATE 
      ,ass.EPISODE_SSID 
      ,ass.[SERVICE] 
      ,ass.SERVICE_DESC 
      ,ass.TEAM_KEY 
      ,ass.PROVIDER_KEY 
      ,CAST(ISNULL(jcc.QUESTIONNUMBER, 0) AS VARCHAR(3)) AS QUESTION_NO 
      ,isnull(CONVERT(VARCHAR(100), replace(replace(CAST(jcc.QUESTIONTEXT AS VARCHAR(650)), char(10), ''), char(13), ' ')), ' ') AS QUESTION_TEXT 
      ,ISNULL(CAST(jcc.ANSWER AS VARCHAR(125)), ' ') AS ANSWER_TEXT 
      ,jcc.MyAssessment AS ASSESSMENT_SSID 
----------------------------------------------------------------------------------------- 

      ,CAST(RIGHT(jcc.getMyCoordtoyPlanVer, 10) AS INT)  AS toy_PLAN_VERSION_SSID  
      ,CAST(RIGHT(jcc.myJcAssessmentContext, 10) AS INT)  AS CONTEXT_FORM_SSID 
-----------------------------------------------------------------------------------------   
      ,ass.RECORD_DATE 
           **,CAST(jcc.getQuestionId AS VARCHAR(300))     AS QUESTION_ID /*NEW Text Column ,this remove the parallelism*/** 
FROM  TEMP_DATABASE.dbo.jsystemReport_toySpell    csp WITH(NOLOCK) 
      INNER JOIN 
      TEMP_DATABASE.dbo.jsystemAssessment      ass WITH(NOLOCK) 
      ON csp.getcustomersId = ass.customersID 
      AND csp.EVENT_SSID = ass.EVENTID 
      LEFT OUTER JOIN 
      SourceFeed.dbo.JcccustomersAssessmentProxy jcc WITH(NOLOCK) 
      ON csp.OID = jcc.getmycoordtoyplanver 

WHERE  NOT EXISTS (SELECT tp1.OID 
         FROM TEMP_DATABASE.dbo.AssessmentTransferPart1 tp1 
         WHERE tp1.OID = jcc.OID) 

UNION ALL 

SELECT  ass.P_KEY 
      ,ass.SS_CODE 
      ,CAST(a.EVENT_SSID AS VARCHAR(11)) AS EVENT_SSID 
      ,CAST(CAST(C.QUESTIONNUMBER AS INT) AS CHAR(3)) AS EVENT_NO 
      ,CAST(ISNULL(CAST(C.TEMPLATEVERSION AS VARCHAR), 0) AS INT) AS TEMPLATEVERSION 
      ,ISNULL(CAST(C.TEMPLATENAME AS VARCHAR(50)), ' ') AS TEMPLATENAME 
      ,a.ASSESSMENT_DATE 
      ,ISNULL(C.ANSWERNUMBER, 0) AS ANSWER_NO 
      ,ass.CASE_SSID 
      ,ass.REL_SSID 
      ,ass.REAL_DATE 
      ,ass.EPISODE_SSID 
      ,ass.[SERVICE] 
      ,ass.SERVICE_DESC 
      ,ass.TEAM_KEY 
      ,ass.PROVIDER_KEY 
      ,CAST(ISNULL(CAST(C.QUESTIONNUMBER AS INT), 0) AS VARCHAR(3)) AS QUESTION_NO 
      ,isnull(CONVERT(VARCHAR(100), CAST(C.QUESTIONTEXT AS VARCHAR(650))), ' ') AS QUESTION_TEXT 
      ,ISNULL(CAST(C.ANSWER AS VARCHAR(125)), ' ') AS ANSWER_TEXT 
      ,a.MyAssessment AS ASSESSMENT_SSID 
----------------------------------------------------------------------------------------- 

      ,CAST(RIGHT(C.getMyCoordtoyPlanVer, 10) AS INT)  AS toy_PLAN_VERSION_SSID  
      ,CAST(RIGHT(C.myJcAssessmentContext, 10) AS INT)  AS CONTEXT_FORM_SSID 
-----------------------------------------------------------------------------------------   
      ,ass.RECORD_DATE 
           **,CAST(c.getQuestionId AS VARCHAR(300))**     AS QUESTION_ID /*NEW Text Column ,this remove the parallelism*/ 
FROM  SourceFeed.dbo.toyClusterReviewAssessment  B WITH(NOLOCK) 
      INNER JOIN 
      SourceFeed.dbo.JcccustomersAssessmentProxy  C WITH(NOLOCK, INDEX=IX_AssessmentProxy_myJcAssessmentContext) 
      ON B.myJCJccUserFormContext = C.myJcAssessmentContext 
      INNER JOIN 
      SourceFeed.dbo.JcccustomersAssessmentScoreProxy D WITH(NOLOCK) 
      ON B.myJCJccUserFormContext = D.myJcAssessmentContext 


      INNER JOIN 
      TEMP_DATABASE.dbo.jsystemReport_toyClusterReviewEvent_AllPersons A WITH(NOLOCK) 
      ON a.myAssessment = B.oid 
      INNER JOIN 
      TEMP_DATABASE.dbo.jsystemAssessment    ass WITH(NOLOCK) 
      ON a.getcustomersId = ass.customersID 
      AND a.EVENT_SSID = ass.EVENTID 
WHERE  NOT EXISTS (SELECT OID 
         FROM (SELECT  tp1.OID 
            FROM TEMP_DATABASE.dbo.AssessmentTransferPart1 tp1 
            UNION ALL 
            SELECT tp2.OID 
            FROM TEMP_DATABASE.dbo.AssessmentTransferPart2 tp2) jcc 
         WHERE jcc.OID = C.OID) 

這是link to the actual execution plan


JccClientAssessmentProxy jcc添加索引WITH(NOLOCK,INDEX = IX_AssessmentProxy_GETMYCOORDCAREPLANVER)後 這裏是the new execution plan

+1

您添加了哪個文本列?你剛剛添加了一列到SELECT子句,它減慢了你的查詢?你必須更具體,像這樣,這是你的問題不容易理解。可能添加SQL小提琴與表結構等 –

+0

getQuestionId是列 – user1254579

+0

觀察標記爲粗體等在格式化的代碼塊中不起作用。 –

回答

1

有問題的部分是:

,CAST(a.getQuestionId AS VARCHAR(300)) AS QUESTION_ID 
    FROM cnlPjccR_Report.dbo.JccClientAssessmentProxy AS a 
     WITH(NOLOCK,INDEX=IX_AssessmentProxy_getMyEventItem) 
    INNER JOIN ... 

和問題重演在你的兩個UNION ALL的子查詢。

您的執行計劃顯示價格昂貴Key lookups

第二種方法是看您可以創建一個「覆蓋索引」是 滿足整個查詢或者至少避免了鍵查找。一個 「覆蓋索引」很簡單,就是擁有所有必要要麼滿足整個查詢或在我們的例子中 列的非聚集索引, 消除對鍵查找操作的需要。一個挑戰是要獲得 列表,這些列是生成密鑰查找的列。您可以通過右擊關鍵 查找運營商做到這一點 在SQL Server Management Studio中(SSMS),然後選擇屬性。然後在屬性窗口中找到輸出 列表行,然後單擊省略號按鈕。 這將打開一個窗口(見下面),其中列出了密鑰查找所要查找的所有列 。您可以使用此列表來幫助您確定是否以及如何創建索引以「覆蓋」查詢或查找關鍵字 。

在你的情況下列768,16列入創建一個覆蓋索引:

[cnlPjccR_Report].[dbo].[JccClientAssessmentProxy].answer; 
[cnlPjccR_Report].[dbo].[JccClientAssessmentProxy].answerNumber; 
[cnlPjccR_Report].[dbo].[JccClientAssessmentProxy].getMyCoordCarePlanVer; 
[cnlPjccR_Report].[dbo].[JccClientAssessmentProxy].getQuestionId; 
[cnlPjccR_Report].[dbo].[JccClientAssessmentProxy].myAssessment; 
[cnlPjccR_Report].[dbo].[JccClientAssessmentProxy].myJcAssessmentContext; 
[cnlPjccR_Report].[dbo].[JccClientAssessmentProxy].questionNumber; 
[cnlPjccR_Report].[dbo].[JccClientAssessmentProxy].questionText; 
[cnlPjccR_Report].[dbo].[JccClientAssessmentProxy].templateName; 
[cnlPjccR_Report].[dbo].[JccClientAssessmentProxy].templateVersion 

可能是你沒有索引包括getQuestionId列,這一事實已在你的查詢執行計劃創建慢Key lookupRID lookup

also herethis answer