2017-01-19 2 views
0

Я использую MS SQL Server, и я изо всех сил пытаюсь найти все реле «In Service» (таблица TRELAY), у которых нет «Active «Настройка запросов (таблица TREQUEST).SQL-запрос для получения записи из первой таблицы, которая не имеет соответствующего подзапроса во второй таблице

TRELAY имеет отношение ко многим отношениям с TREQUEST. Записи в TREQUEST могут иметь различные статусы («Не готов», «Ожидание», «Актив», «Заменено»).

Я пробовал подзапросы и соединения (слева/слева), но я не могу получить запрос, чтобы вернуть отдельную запись ретрансляции без активных записей запроса настроек. Он возвращает повторяющиеся записи Relay со всеми дублирующимися запросами на замещение.

Я пытался использовать Не как «Активный», но я получаю несколько записей релейных записей.

T.S06 is the Status from the TRELAY table (string field) 
R.S03 is the Setting Status from the TREQUEST tabe (string field) 

SELECT T.ID, T.S06, R.S03 FROM TRELAY T 
LEFT JOIN TREQUEST R ON R.RELAYID = T.ID AND R.S03 NOT LIKE '%ACTIVE%' 
WHERE T.S06 LIKE '%IN SERVICE%' 

Результат вышеупомянутого запроса:

Relay ID || Status  || Setting Status 
======================================== 
303  || In Service || Superseded 
307  || In Service || Superseded 
307  || In Service || Superseded 
307  || In Service || Superseded 

Я признателен за любую помощь вы можете предоставить. Пожалуйста, дайте мне знать, если вам нужна дополнительная информация.

Спасибо, Joe C.

+0

Ваш запрос, вероятно, будет работать, если вы просто изменили свой SELECT на 'SELECT DISTINCT', чтобы он захватывал только уникальные строки. – Santi

+0

Не повезло с отличием. Он удалил один из ID Relay 307, но все же вернул 2 из них. –

+0

Я вижу. Затем взгляните на ответ AdaTheDev. На самом деле, как правило, лучше избегать «LIKE» только для эффективности. «НЕ СУЩЕСТВУЮЩИЕ» могут быть правильной методологией здесь. – Santi

ответ

0

Посмотрите в использовании NOT EXISTS, как такого рода подход:

SELECT x 
FROM Table1 t1 
WHERE NOT EXISTS(
    SELECT * FROM Table2 t2 
    WHERE t2.Identifier = t1.Identifier AND...any other conditions... 
) 

Который просто сказать, «найти меня все строки в таблице 1, где есть не соответствующая запись в Таблице 2 "- вам просто нужно указать точные условия в том, что пункт NOT EXISTS

+0

Я могу получить подзапрос правильно, по крайней мере, я так думаю. Он возвращает те записи, которые находятся в службе, и у них нет запроса активной настройки: –

+0

SELECT * FROM TREQUEST R INNER JOIN TRELAY ON R.RELAYID = TRELAY.ID WHERE R.RELAYID = TRELAY.ID И R.S03 НЕ НРАВИТСЯ '% ACTIVE%' AND TRELAY.S06 LIKE '% IN SERVICE%' –

+0

, но когда я инкапсулирую его внутри внешнего запроса, я не могу получить разные ретранслируемые записи. SELECT * FROM TRELAY ГДЕ TRELAY.S06 LIKE '% IN SERVICE%' и существует в ( SELECT * FROM TREQUEST R INNER JOIN TRELAY ПО R.RELAYID = TRELAY.ID ГДЕ R.RELAYID = TRELAY.ID и R. S03 НЕ НРАВИТСЯ «% АКТИВНО%» И TRELAY.S06 НРАВИТСЯ «% В СЕРВИСЕ%» ) –

0

Вы близко, попробуйте инвертировать вашу логику. Сначала найдите все свои отдельные Active RelayID. Затем Left Присоедините их к вашему T.id и возьмите только несоответствия.

SELECT T.ID, T.S06 
FROM TRELAY as T 
LEFT JOIN 
(SELECT Distinct RELAYID FROM TREQUEST WHERE S03 LIKE '%ACTIVE%') as R 
ON T.ID = R.RELAYID 
WHERE T.S06 LIKE '%IN SERVICE%' AND R.RELAYID IS NULL; 

R.RELAYID IS NULL проверяет наличие несоответствия. Таким образом, вы получаете все свои T.ID из таблицы TRELAY.

Если вам нужно вернуться назад и захватить все остальные «Состояние настройки» для каждого T.ID, вы можете связать этот набор с таблицей TREQUEST.

Надежда, что помогает :)

* EDIT *

В ответ на комментарий:

"When I use (Select T.ID, T.S06, TREQUEST.S03 FROM TRELAY AS T, TREQUEST) I get a multi-part identifier T.ID could not be bound. Do I need to do another join before the Left Join."

Да, вы бы сделать INNER JOIN к SQL я написал выше , Ниже приведен код, который присоединился бы к вашему набору хороших T.ID назад к таблице TREQUEST и вытащил все хорошие значения S03, связанные с каждым уникальным T.ID. Я обозначил ваши хорошие значения T.ID как GoodTID. И я обозначил вашу новую ссылку на таблицу TREQUEST как GoodR.

SELECT GoodTID.ID, GoodTID.S06, GoodR.S03 
FROM TREQUEST as GoodR 
INNER JOIN 

(SELECT T.ID, T.S06 
FROM TRELAY as T 
LEFT JOIN 
(SELECT Distinct RELAYID FROM TREQUEST WHERE S03 LIKE '%ACTIVE%') as R 
ON T.ID = R.RELAYID 
WHERE T.S06 LIKE '%IN SERVICE%' AND R.RELAYID IS NULL) as GoodTID 

ON GoodTID.ID = GoodR.RELAYID; 

Этот код даст вам все коды RELAYID-х и S03, которые IN SERVICE и не ACTIVE.

Дайте мне знать, если вам нужно больше объяснений. Надеюсь, это поможет. :)

+0

Спасибо, это действительно помогает ... Я думаю. Мне нужно разбить запросы, чтобы убедиться, что он извлекает только те записи, которые я хочу. Один вопрос, может быть, вы можете помочь. Как присоединиться к таблице TREQUEST в исходной инструкции select. Когда я использую (выбираю T.ID, T.S06, TREQUEST.S03 FROM TRELAY AS T, TREQUEST), я получаю многочастный идентификатор T.ID не может быть связан. Мне нужно сделать еще одно соединение перед левым соединением. –

+0

Я отредактировал вышеупомянутый ответ, чтобы показать вам, как «INNER JOIN» набор уникальных хороших T.ID вернулся в таблицу TREQUEST и покажет все ваши коды «В службе», а не «Активные» S03. – abraxascarab

+0

Спасибо. Я хочу сделать больше тестов, чтобы убедиться, что он работает правильно, но все, кажется, в порядке. Я очень ценю помощь. Я должен тебе виртуальное пиво. :) –

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

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