with total as (
select *
from users a left join edges b on a.user_id = b.user_a_id
union
select *
from users a left join edges b on a.user_id = b.user_b_id
)
select user_id
,count(user_b_id) as num_friends
from total
group by 1
order by 2 desc , user_id asc ;
union 을 사용했지만 union all 을 사용하는 것이 좀 더 성능상으로 좋기에 다시 한번 작성해보았다.
with total as (
select user_a_id as user_id
,count(user_b_id) as cnt
from edges
group by user_a_id
union all
select user_b_id as user_id
,count(user_a_id) as cnt
from edges
group by user_b_id
)
select user_id
,ifnull(sum(cnt), 0) as num_friends
from users b left join total using(user_id)
group by user_id
order by 2 desc , 1 asc;
관건은 모든 사용자에 대한 집계 값이 출력되어야 한다는 점이기 때문에 left join 과 union함수를 쓰는 부분을 염두해둬야 한다.
union - 중복 행을 없애주면서 합쳐준다.
union all - 중복 행을 없애지않고 합친 그대로 출력
** UNION ALL 이 중복제거하지 않기 때문에 UNION 보다 속도가 빠르다. **
'coding > sql 코딩테스트' 카테고리의 다른 글
[리트코드] 184. Department Highest Salary (0) | 2025.02.07 |
---|---|
[solvesql] 유량(Flow)와 저량(Stock) (0) | 2025.01.31 |
[리트코드] 196. Delete Duplicate Emails (0) | 2025.01.23 |
[리트코드] 178. Rank Scores (0) | 2025.01.23 |
[solvesql] 게임 개발사의 주력 플랫폼 찾기 (0) | 2025.01.13 |