SQL Выберите Условие Вопрос

У меня есть быстрый вопрос об условии выбора оператора.

У меня есть следующая таблица со следующими пунктами. Мне нужно получить идентификатор объекта, который совпадает с идентификаторами обоих типов.

TypeId  ObjectId
1       10
2       10
1       11

Поэтому мне нужно получить оба объекта 10, потому что они соответствуют идентификаторам типов 1 и 2.

SELECT ObjectId
FROM Table
WHERE TypeId = 1
AND TypeId = 2

Очевидно, что это не работает, потому что не будет соответствовать обоим условиям для одной и той же строки. Как мне выполнить этот запрос? Также обратите внимание, что я могу передать 2 или более идентификатора типа, чтобы сузить результаты.

4 ответа

Автообъединение:

SELECT t1.ObjectId 
FROM Table AS t1
INNER JOIN Table AS t2
    ON t1.ObjectId = t2.ObjectId
    AND t1.TypeId = 1 
    AND t2.TypeId = 2 

Обратите внимание, что вы хотите, чтобы поведение работало при передаче значений, но это только начало.

Я проголосовал за ответ от @Cade Roux, и вот как я это сделаю.

Но FWIW, вот альтернативное решение:

SELECT ObjectId
FROM Table
WHERE TypeId IN (1, 2)
GROUP BY ObjectId
HAVING COUNT(*) = 2;

Предполагая уникальность над TypeId, ObjectId,


Re комментарий от @Josh, что ему может понадобиться искать три или более TypeId ценности:

Решение с использованием JOIN требуется объединение для каждого значения, которое вы ищете. Решение выше с использованием GROUP BY может быть проще, если вы обнаружите, что ищете все большее число значений.

Этот код написан с учетом Oracle. Это должно быть достаточно общим для других разновидностей SQL

select t1.ObjectId from Table t1
join Table t2 on t2.TypeId = 2 and t1.ObjectId = t2.ObjectId
where t1.TypeId = 1;

Чтобы добавить дополнительные TypeIds, вам просто нужно добавить еще одно объединение:

select t1.ObjectId from Table t1
join Table t2 on t2.TypeId = 2 and t1.ObjectId = t2.ObjectId
join Table t3 on t3.TypeId = 3 and t1.ObjectId = t3.ObjectId
join Table t4 on t4.TypeId = 4 and t1.ObjectId = t4.ObjectId
where t1.TypeId = 1;

Важное примечание: по мере добавления новых объединений производительность будет сильно снижаться.

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

SELECT ObjectId
FROM (SELECT distinct ObjectId, TypeId from Table)
WHERE TypeId IN (1, 2)
GROUP BY ObjectId
HAVING COUNT(*) = 2;

Его способ сделать это лучше масштабируется по мере увеличения количества типов.

Попробуй это

Пример ввода:(Случай 1)

declare @t table(Typeid int,ObjectId int)
insert into @t 
    select 1,10 union all select 2,10  union all    
    select 1,11 
select * from @t 

Пример ввода:(Случай 2)

declare @t table(Typeid int,ObjectId int)
insert into @t 
    select 1,10 union all select 2,10  union all 
    select 3,10 union all select 4,10  union all 
    select 5,10 union all select 6,10  union all 
    select 1,11 union all select 2,11  union all 
    select 3,11 union all select 4,11  union all 
    select 5,11 union all select 1,12  union all 
    select 2,12  union all select 3,12 union all 
    select 4,12  union all select 5,12 union all 
    select 6,12  
select * from @t

Пример ввода:(Случай 3)[Дубликаты записей есть]

declare @t table(Typeid int,ObjectId int)
insert into @t 
    select 1,10 union all select 2,10  union all 
    select 1,10 union all select 2,10 union all
    select 3,10 union all select 4,10  union all 
    select 5,10 union all select 6,10  union all 
    select 1,11 union all select 2,11  union all 
    select 3,11 union all select 4,11  union all 
    select 5,11 union all select 1,12  union all 
    select 2,12  union all select 3,12 union all 
    select 4,12  union all select 5,12 union all 
    select 6,12  union all select 3,12 

Для случая 1 выход должен быть 10

Для случаев 2 и 3 выходное значение должно быть 10 и 12

Запрос:

select X.ObjectId from 
(
select 
            T.ObjectId
            ,count(ObjectId) cnt
from(select distinct ObjectId,Typeid from @t)T
where T.Typeid in(select Typeid from @t)
group by T.ObjectId )X
join (select max(Typeid) maxcnt from @t)Y
on X.cnt = Y.maxcnt
Другие вопросы по тегам