仅选择所有行共有的条目

时间:2017-11-11 09:10:59

标签: sql oracle

您好我有这个表,并且只想查询所有行共有的条目(Log Id)。

 Log Id   Person Id  Main(Y/N)  Sex    Rel       
   01           21   Y           M     ATH       
   02           21   Y           M     ATH       
   03           21   Y           F     ATH       
   04           21   Y           M     ATH       
   05           21   Y           F     ATH       

预期结果如下:

PersonId  Y/N   Sex   Rel     
     21    Y     -    ATH     

你看我想只显示所有行的共同内容,否则为null。这只是一个非常复杂的查询的一部分。以下是一个大问题。

 Log Id   Person Id  Main(Y/N)  Sex    Rel       
   01           21   Y           M     ATH       
   02           21   Y           M     ATH       
   03           21   Y           F     ATH       
   04           21   Y           M     ATH       
   05           21   Y           F     ATH       
   01           22   N           M     ATH       
   02           22   N           M     ATH       
   03           22   N           M     ATH       
   04           22   N           M     ATH       
   05           22   N           M     ATH       

预期结果如下:

PerId  Y/N  S   Rel    
  21    Y   -   ATH    
  22    N   M   ATH    

2 个答案:

答案 0 :(得分:1)

以下查询应该有效:

select personId,
       (case when count(distinct main)>1 then '' else main end) as Main,
       (case when count(distinct sex) >1 then '' else sex  end) as Sex,
       (case when count(distinct religion)>1 then '' else religion end) as Religion
from yourTableName
group by personId;

<强>结果:

    personId | Main | Sex | Religion
     21      |  Y   |     |  ATH
     22      |  N   |  M  |  ATH

Click here for DEMO

ORACLE SOLUTION:(正如@MarmiteBomber所建议的那样)

select personId,
       (case when count(distinct main)=1 then max(main) else ' ' end) as Main,
       (case when count(distinct sex)=1 then max(sex) else ' ' end) as Sex,
       (case when count(distinct religion)=1 then max(religion) else ' ' end) as Religion
from t
group by personId;

DEMO in Oracle

希望它有所帮助!

答案 1 :(得分:0)

我会把它写成:

select personId,
       (case when min(main) = max(main) then max(main) end) as Main,
       (case when min(sex) = max(sex) then max(sex) end) as Sex,
       (case when min(religion) = max(religion) then max(religion) end) as Religion
from yourTableName
group by personId;

注意:这会使用NULL表示未知值。我认为这更符合SQL。如果你真的想要一个连字符,你可以使用else '-'

为什么使用min()max()代替count(distinct)?原因很简单:性能。 count(distinct)比其他聚合操作更昂贵(因为中间结果必须存储所有可能值的列表)。