mysql left join 去重_SQL LEFT JOIN 数据去重复

SQL LEFT JOIN 数据去重复

2020-11-05 05:15:38.0

实例:查询当前用户参与过的流程实例(instance)

关系:每个实例 (instance)对应多个任务(task),task关联办理人(userId)

select inst.*

from instance inst

left join task t on inst.id = t.inst_id

where t.user_id = #{userId}

这样查询后,如果一个人办理同一个流程中的多个任务,则会重复查出相同的instance。

其实 join 关键词查询“一对多”关系的数据,查询之后的结果的记录数,是和“ 多端 ”保持一致的,也就是“一端”的数据会重复。

left join、right join 只是选择保留下左/右端不符合join条件的多余数据,与数据重复问题无关,inner join 、outter join 也是。 所以数据的数据去重复,无法通过这几个关键词解决。

实例分析解决

有用户与角色的“一对多”,left join查询如下:

-- LEFT JOIN 查询一对多的关系,“一端”会重复

SELECT

u.id,

u.mc,

u.nl,

u.lxfs,

u.bzsm,

r.id roleId,

r.jsmc,

r.sm

FROM

test_user u

LEFT JOIN test_role r ON u.id = r.user_id

550c811b8c438da50a1ab12c0f56a5ff.png

解决方法一: 结果使用group by 去重

将查询结果作为中间表,使用group by 进行去重:

-- 关联查询出结果,再使用group by 去重

select tmp.* from (

SELECT

u.id,

u.mc,

u.nl,

u.lxfs,

u.bzsm,

r.id roleId,

r.jsmc,

r.sm

FROM

test_user u

LEFT JOIN test_role r ON u.id = r.user_id

) tmp group by tmp.id;

8664ef98ec9b1f77f0ede96bf3fff5f0.png

解决方法二: “多端”使用group by 去重

去重“多端”的数据(中间表变成一对一),再关联。分析重复的原因,就是就是有多个角色对应同一个user_id,所以,将角色去重,变成“一对一”关系,再关联查询。

-- 去重“多端”的数据(中间表变成一对一),再关联

SELECT

u.id,

u.mc,

u.nl,

u.lxfs,

u.bzsm,

tmp_r.id roleId,

tmp_r.jsmc,

tmp_r.sm

FROM

test_user u

LEFT JOIN (

select r.* from test_role r group by r.user_id

) tmp_r ON u.id = tmp_r.user_id

4d9b15bdab333b372d3066ccfd91d103.png

解决方法三:使用 EXISTS

上述两种方法,其实对“多端”保留哪条数据是没有要求的(除非自己再重新定义test_role的去重方法),所以,与exists的查询效果相同。

尤其在开篇的实例中,“ 查询当前用户参与过的流程实例(instance) ”,即与参与哪个task无关时,使用exists更符合业务逻辑。

-- exists

SELECT u.*

FROM

test_user u

WHERE EXISTS (

select * from test_role r where r.user_id = u.id

);

2d2d9bbad805c0939d552091099f9ff5.png

2020-11-05 05:15:38.0

  • 4
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值