2016-06-28 2 views
2

У меня есть несколько операторов JOIN в одном запросе, и я должен проверить две настройки в JOIN. Как это сделать наилучшим образом?Sql Оптимизация запроса Проблема в JOIN

table: WebSettings 
------------------------------------------------------- 
Name   | Setting | InstID | WebSettingID 
------------------------------------------------------- 
'EnableError' | 2 | 1111 | 1 
'ErrorsSetting' | 0 | 2121 | 2 

Index : 

InstID 
WebSettingID (InstID) 


table: InstProd 
------------------------------------------------------- 
InstitutionID | Name 
------------------------------------------------------- 
1111  | 'Bank of Ind' 
2121  | 'IOB' 


Index : 

InstitutionID 


SELECT 

Column1, 
DATEADD(.....) 

FROM 
dbo.InstProd I 
INNER JOIN dbo.WebSettings WS1 ON 
WS1.InstitutionID = I.InstID AND 
WS1.Name = 'EnableError' AND WS1.Setting=2 
INNER JOIN dbo.WebSettings WS2 ON 
WS2.InstitutionID = I.InstID AND 
WS2.Name = 'ErrorsSetting' AND WS2.Setting=0 
WHERE..... 

Я хочу проверить одну WebSettings = 2 и other = 0 в JOIN

Есть ли лучшее решение сделать это?

+1

Пожалуйста, объясните лучше вы спрашиваете. Что вы хотите в качестве вывода? –

+0

Добавить определения таблиц и индексы! – jarlh

+0

Этот код даже не запускается. Вам не хватает предложений AND/OR в коде. –

ответ

1

Да, вы не должны присоединиться WebSettings дважды, если вы не отправлял свой ожидаемый результат, так что я не знаю точно, что делать, но изменить это:

SELECT <column1>,<column2>, 
     MAX(CASE WHEN ws.Name = 'EnableError' AND ws.settings = 2 THEN <YourDesiredColumn> END) as enable_column, 
     MAX(CASE WHEN ws.Name = 'ErrorsSetting' AND ws.settings = 0 THEN <YourDesiredColumn2> END) as Errors_column 
FROM bo.InstProd I 
INNER JOIN dbo.WebSettings WS1 ON 
WS1.InstitutionID = I.InstID AND 
(WS.Name,ws.setting) in (('EnableError',2),('ErrorsSetting',0)) 
GROUP BY <column1>,<column2> 

Это будет дайте столбцам разрешения и ошибки в той же строке, как и ваш запрос.

+0

Я вернусь к этому после проверки. Спасибо – Keppy

+0

Я пробовал это и не видел улучшения в производительности по сравнению с моим скриптом и решил пойти с моим. Спасибо за поддержку. – Keppy

1

Минимизация JOINS может дать результат, что вы ожидаете, если вы не используете WS2

SELECT 
Column1, 
DATEADD(.....) 

FROM 
dbo.InstProd I 
INNER JOIN dbo.WebSettings WS1 ON WS1.InstitutionID = I.InstID 
           AND (WS1.Name = 'EnableError' 
            AND WS1.Setting = 2) 
           OR (WS1.Name = 'ErrorsSetting' 
            AND WS1.Setting = 0) 
WHERE..... 
+0

Я вернусь к этому после проверки. Спасибо – Keppy

+1

Я пробовал это и не видел улучшения в производительности по сравнению с моим сценарием и решил пойти с моим. Спасибо за поддержку. – Keppy

0

Вы можете принять решение не использовать JOIN, как мои следующие решения

Если вы хотите, чтобы все InstProd с EnableError = 2 и ErrorSettings = 0

Попробуйте следующее:

SELECT I.* 
FROM InstProd I 
WHERE EXISTS 
    (SELECT 'EnableError = 2' 
     FROM WebSettings WS 
     WHERE WS.InstID = I.InstitutionID 
     AND WS.Name = 'EnableError' AND WS.Setting = 2) 
AND EXISTS 
    (SELECT 'EnableError = 2' 
     FROM WebSettings WS 
     WHERE WS.InstID = I.InstitutionID 
     AND WS.Name = 'ErrorSettings' AND WS.Setting = 0) 

Если вы хотите, чтобы все InstProd с проверкой о два параметра значения

Попробуйте это:

SELECT I.*, 
CASE 
    WHEN 
     (SELECT COUNT(1) 
     FROM WebSettings WS 
     WHERE WS.InstID = I.InstitutionID 
     AND WS.Name = 'EnableError' AND WS.Setting = 2) > 0 
     AND 
     (SELECT COUNT(1) 
     FROM WebSettings WS 
     WHERE WS.InstID = I.InstitutionID 
     AND WS.Name = 'ErrorSettings' AND WS.Setting = 0) > 0 
    THEN 'OK' 
    ELSE 'KO' 
END 
FROM InstProd I 
+0

Спасибо. С точки зрения производительности, какой из них вы предложите? ПРИСОЕДИНЯЙТЕСЬ или СУЩЕСТВУЕТЕ, если число моих записей велико? – Keppy

+0

Я думаю, что не существует команды для всей ситуации. Зависит от того, что вы хотите, в этом случае существует условие, это нормально для первого случая (потому что вы не показываете эту информацию, но используете только для условий), для второго случая, который я предпочитаю (потому что это только два поля), подзапрос в select список полей. С помощью JOIN вы должны применить группу по отдельному предложению, чтобы отбросить дублированные строки –

Смежные вопросы