Oracle 18c查询COLUMNB全属于指定集合的去重COLUMNA值方案
方案1:允许值写死在查询中(无需关联tableB)
核心逻辑是分组后判断是否存在不符合要求的COLUMNB:
SELECT COLUMNA FROM TABLEA GROUP BY COLUMNA HAVING MAX(CASE WHEN COLUMNB NOT IN (1172, 1011, 1037) THEN 1 ELSE 0 END) = 0;
说明:对每个COLUMNA分组统计,只要存在任意一个COLUMNB不在允许集合内,就会被HAVING条件过滤,GROUP BY天然保证返回的COLUMNA去重,不需要额外加DISTINCT。
方案2:允许值存储在tableB中
如果允许值存放在单列tableB(列名为values),可以用左连接匹配的方式:
SELECT a.COLUMNA FROM TABLEA a LEFT JOIN tableB b ON a.COLUMNB = b."values" GROUP BY a.COLUMNA HAVING COUNT(b."values") = COUNT(*);
说明:左连接后,只要某行COLUMNB不在tableB的允许值范围内,对应的b.values就为NULL,COUNT统计时NULL不会被计数,COUNT(b.values)和COUNT(*)相等就说明该COLUMNA下所有COLUMNB都符合要求。
方案3:NOT EXISTS写法(逻辑更直观)
SELECT DISTINCT COLUMNA FROM TABLEA a WHERE NOT EXISTS ( SELECT 1 FROM TABLEA a2 WHERE a2.COLUMNA = a.COLUMNA AND a2.COLUMNB NOT IN (1172, 1011, 1037) );
如果使用tableB的话调整子查询即可:
SELECT DISTINCT COLUMNA FROM TABLEA a WHERE NOT EXISTS ( SELECT 1 FROM TABLEA a2 WHERE a2.COLUMNA = a.COLUMNA AND NOT EXISTS ( SELECT 1 FROM tableB b WHERE b."values" = a2.COLUMNB ) );
原写法问题说明
你原来的写法存在两个问题:
- 分组后不需要再加窗口函数
COUNT (*) OVER (PARTITION BY columnA),属于冗余逻辑 HAVING COUNT (*) > 1的条件有误:如果某COLUMNA仅有一个符合要求的COLUMNB(比如只有1037),会被这个条件误过滤,不符合需求。
内容的提问来源于stack exchange,提问作者milheiros
相关产品推荐
相关产品推荐

