Как вы помещаете литералы в результат набора результатов SQL, основанный на том, какая таблица была объединена для создания строки? - PullRequest
2 голосов
/ 17 ноября 2009

У меня есть 3 таблицы, одна из которых представляет «супертип», со столбцом идентификатора. Две другие таблицы - это подтипы, со столбцом идентификатора, который является внешним ключом для таблицы супертипа, плюс столбец, специфичный для подтипа.

Мне нужен запрос, который возвращает все данные, а также столбец, который я могу использовать в качестве дискриминатора, который сообщает мне, из какой таблицы получена строка.

Так, например, как я могу изменить это:

SELECT * from SUPER S 
left outer join SUB_1 S1 on S.ID = S1.ID
left outer join SUB_2 S2 on S.ID = S2.ID

Что возвращает мне это:

ID    SUB_COL_1  SUB_COL_2
====  =========  =========
0001  value x    NULL
0002  value y    NULL
0003  NULL       value z

Во что-то, что добавит столбец дискриминатора с некоторыми жестко закодированными литеральными значениями, например:

ID    DISCRIMINATOR  SUB_COL_1  SUB_COL_2
====  =============  =========  =========
0001  SUBTYPE_1      value x    NULL
0002  SUBTYPE_1      value y    NULL
0003  SUBTYPE_2      NULL       value z

Мне не разрешается каким-либо образом изменять модель данных. Я также не могу выполнить какую-либо постобработку путем программного тестирования NULLS после факта. Мне нужно работать с таблицами, как есть, и производить точный набор результатов, показанный выше. Я использую Oracle 11g, если это как-то повлияет на ответ.

Ответы [ 4 ]

4 голосов
/ 17 ноября 2009

Вы можете добавить:

CASE IF S1.ID IS NULL THEN 'SUBTYPE_1' ELSE 'SUBTYPE_2' END AS DISCRIMINATOR, 

в начале вашего SELECT предложения.

1 голос
/ 18 ноября 2009

Я бы, вероятно, добавил идентификатор к данным каждой таблицы в подзапросе до его присоединения.

SELECT * from 
    (select *, 'SUPER' as DISCRIMINATOR from SUPER ) S 
left outer join 
    (select *, 'SUBTYPE1' as DISCRIMINATOR from SUB_1 ) S1 
    on S.ID = S1.ID
left outer join 
    (select *, 'SUBTYPE1' as DISCRIMINATOR from SUB_2 ) S2 
    on S.ID = S2.ID
1 голос
/ 17 ноября 2009

Обычно я делаю это с помощью запроса UNION

Select S.ID, SUBTYPE_1 as DISCRIMINATOR, S1field1 as SUB_COL_1, null as SUB_COL_2  
from SUPER S 
join SUB_1 S1 on S.ID = S1.ID
union all 
Select S.ID, SUBTYPE_2 as DISCRIMINATOR, null as SUB_COL_1, S2.field1 as SUB_COL_2  
from SUPER S 
join SUB_2 S2 on S.ID = S2.ID
1 голос
/ 17 ноября 2009

Может быть, это то, что вы ищете ... вам, возможно, придется внести несколько изменений, чтобы заставить его работать на Oracle.

SELECT case coalesce(SUB_COL_1,'') when '' then 'SUBTYPE_2'  else 'SUBTYPE_1' end,  * from SUPER S 
left outer join SUB_1 S1 on S.ID = S1.ID
left outer join SUB_2 S2 on S.ID = S2.ID
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...