繁体   English   中英

ORACLE SQL比较同一表中的两行或更多行

[英]ORACLE SQL compare two or more rows in same table

我有一个值与此类似的表

Uname | Grp_ID | Role_ID
---------------------
usr1  | 10     | 1032
usr1  | 10     | 1034
usr1  | 20     | 1032
usr1  | 20     | 1034
usr1  | 30     | 1032
usr1  | 40     | 1032
usr1  | 50     | 1034
usr1  | 50     | 1034
usr1  | 60     | 1018
usr1  | 70     | 1057

我想要输出具有1032和1034(两者)作为角色ID的Grp_ID,例如,

Grp_ID 10 has 1032 and 1034 as ROle_IDs
Grp_ID 20 has 1032 and 1034 as ROle_IDs

Grp_ID 30、40、50、60、70不同时具有1032和1034作为Role_ID

我已经尝试过使用内部联接和“具有”,但似乎没有得到我想要的。

Select t1.uname, t2.grp_id, t1.role_id from table_name t1 
left join table_name t2 on t1.grp_is = t2.grp_id
Where t1.role_id = 1032 and t2.role_id = 1034

您需要做的是在组ID上将表连接到自身,然后过滤包含两个角色ID的行。 联接中涉及的每个表都扮演不同的角色。 如果需要过滤3个值,则需要3个表子句(两个联接)。

WITH thetable AS (
  SELECT 10 grpid, 1032 roleid FROM dual UNION ALL
  SELECT 10 grpid, 1034 roleid FROM dual UNION ALL
  SELECT 20 grpid, 1032 roleid FROM dual UNION ALL
  SELECT 20 grpid, 1034 roleid FROM dual UNION ALL
  SELECT 30 grpid, 1032 roleid FROM dual UNION ALL
  SELECT 40 grpid, 1032 roleid FROM dual UNION ALL
  SELECT 50 grpid, 1034 roleid FROM dual UNION ALL
  SELECT 50 grpid, 1034 roleid FROM dual UNION ALL
  SELECT 60 grpid, 1018 roleid FROM dual UNION ALL
  SELECT 70 grpid, 1057 roleid FROM dual
)
SELECT t1.grpid, t1.roleid, t2.roleid
FROM thetable t1
JOIN thetable t2 ON t1.grpid = t2.grpid
WHERE t1.roleid = 1032 AND t2.roleid = 1034;


groupid  roleid  roleid_1
10       1032    1034
20       1032    1034

我喜欢使用group byhaving来解决这些问题。 在这种情况下:

select grp_id
from tbl 
where role_id in (1032, 1034)
group by grp_id 
having count(distinct role_id) = 2;

我发现这种方法可以推广到套集问题的许多变体中。

只是提供不同的答案:

SELECT GrpID FROM theTable WHERE roleId = 1032
INTERSECT
SELECT GrpID FROM theTable WHERE roleID = 1034

要么

SELECT 'Grp_ID '|| GRPID ||' has 1032 and 1034 as Role_IDs' 
FROM theTable 
WHERE roleId = 1032
INTERSECT
SELECT 'Grp_ID '|| GRPID ||' has 1032 and 1034 as Role_IDs' 
FROM theTable 
WHERE roleID = 1034

如果您需要问题中的全文...

但是我不是很喜欢在SQL表示层中添加这样的文本,所以应该注意这一点。

就像@jarlh所说的那样。 在这里我不使用uname过滤器

with tbl (Uname,Grp_ID,Role_ID) as 
(   select 'usr1',10,1032 from dual union all
    select 'usr1',10,1034 from dual union all
    select 'usr1',20,1032 from dual union all
    select 'usr1',20,1034 from dual union all
    select 'usr1',30,1032 from dual union all
    select 'usr1',40,1032 from dual union all
    select 'usr1',50,1034 from dual union all
    select 'usr1',50,1034 from dual union all
    select 'usr1',60,1018 from dual union all
    select 'usr1',70,1057 from dual
)
--Query
select grp_id
 ,count(distinct role_id) as count_dist_role_id 
from tbl 
where Role_ID in (1032,1034)
group by grp_id 
having count(distinct role_id)=2

产量

+--------+--------------------+
| GRP_ID | COUNT_DIST_ROLE_ID |
+--------+--------------------+
|     20 |                  2 |
|     10 |                  2 |
+--------+--------------------+

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM