month ASC, rnk ASC반별 평균 점수로 등수를 매기고, 지난달 등수보다 올랐나 내렸나를 본다.
| 월 | 채널 | 평균 | 등수 | 지난달 등수 | 변동 |
|---|---|---|---|---|---|
| 1월 | referral | 23,000 | 1 | (없음) | (없음) |
| 2월 | referral | 23,200 | 1 | 1 | 0 |
| 2월 | sns | 16,900 | 4 | 3 | -1 (내려감) |
변동 = 지난달 등수 − 이번달 등수. 등수가 1→4 로 내려가면 음수.
RANK() OVER (PARTITION BY 월 ORDER BY 평균 DESC).LAG(등수) OVER (PARTITION BY 채널 ORDER BY 월).묻는 것 · 윈도우를 두 단계로 겹쳐 쓸 줄 아는가.
RANK() → 파티션은 월.LAG(rnk) → 파티션은 채널. 파티션 기준이 다르다.WITH a AS (
SELECT DATE_FORMAT(p.paid_date, '%Y-%m-01') AS mm, u.channel,
ROUND(SUM(p.amount) / COUNT(DISTINCT p.user_id), 2) AS arppu
FROM payments p JOIN users u ON u.user_id = p.user_id
GROUP BY mm, u.channel
),
r AS (
SELECT mm, channel, arppu,
RANK() OVER (PARTITION BY mm ORDER BY arppu DESC) AS rnk
FROM a
)
SELECT DATE_FORMAT(mm, '%Y-%m') AS month, channel, arppu, rnk,
LAG(rnk) OVER (PARTITION BY channel ORDER BY mm) AS prev_rnk,
LAG(rnk) OVER (PARTITION BY channel ORDER BY mm) - rnk AS rank_change
FROM r
ORDER BY mm, rnk;rank_change 부호 방향을 문제대로. 여기서는 ‘전월 − 이번달’이라 오르면 양수.COUNT(DISTINCT user_id). 결제 건수가 아니다.“전월 대비 매출 순위 변동”, “주간 랭킹 변화” 전부 같은 2단 구조.