我正在寻找SQL查询的一些帮助。 (我正在使用Oracle。)
我有一个包含2个不同选择状态的联合查询。结果数据如下所示:
Col1 Col2 Col3
XXX ValA Val1
XXX ValB Val2
YYY ValA Val1
YYY ValA Val2
在此设置中,Col1 = XXX是默认值,Col1 = YYY是实际值。实际值(YYY)应该优先于默认值。实际值通过第2列和第3列定义。
我希望将这些结果归结为以下内容:
Col1 Col2 Col3
XXX ValB Val2
YYY ValA Val1
YYY ValA Val2
请注意,第一行已删除...这是因为有一个实际值(第3行中的YYY)占用了默认值(XXX)。
有关如何处理此事的任何想法?
答案 0 :(得分:2)
您想过滤掉col2和col3与XXX和其他值一起显示的所有行。
您可以使用分析函数在子查询中执行适当的计数来实现此过滤器:
select col1, col2, col3
from (select t.*,
count(*) over (partition by col2, col3) as numcombos,
sum(case when col1 = 'XXX' then 1 else 0 end) over (partition by col2, col3) as numxs
from t
) t
where numcombos = numxs or (col1 <> 'xxx')
答案 1 :(得分:1)
我的直觉是使用分析函数:
select distinct
first_value(col1)
over (partition by col2, col3
order by case col1
when 'XXX' then 1
else 0 end asc) as col1,
col2,
col3
from table1
但是,如果表很大并且已建立索引,那么使用完全外连接解决此问题可能更好(这是可能的,因为只有两个可能的值):
select coalesce(rl.col1, dflt.col1) as col1,
coalesce(rl.col2, dflt.col2) as col2,
coalesce(rl.col3, dflt.col3) as col3
from (select * from table1 where col1 = 'XXX') dflt
full outer join (select * from table1 where col1 <> 'XXX') rl
on dflt.col2 = rl.col2 and dflt.col3 = rl.col3;
答案 2 :(得分:0)
我认为你可以使用这样的技巧:
select
case when
max(case when col1<>'XXX' then col1 end) is null then 'XXX' else
max(case when col1<>'XXX' then col1 end) end as col1,
col2,
col3
from
your_table
group by col2, col3
我将默认值转换为null,然后按col3分组。 null和值之间的最大值是您要查找的值。这适用于您的示例数据,但它可能不是您正在寻找的,它取决于您的实际数据。