题解 | 统计用户从访问到下单的转化率
统计用户从访问到下单的转化率
https://www.nowcoder.com/practice/eaff8684aed74e208300f2737edbb083
select date, concat(round(id_cnt/vi_cnt*100,1),'%') cr from ( select date(order_time) date, count(distinct m.user_id) id_cnt, count(distinct n.user_id) vi_cnt from order_tb m join visit_tb n on date(m.order_time)=date(n.visit_time) group by date(m.order_time) ) as t order by date
1.小数转化为百分数:先除,再乘100,再保留小数位数,最后拼接字符串%
2.本题中不再是按user_id 联结表,而是按照time联结,因为要求是对每天的订单进行计数,与到底是谁的订单无关
3.在计数时都要去重,访问人数需要去重,访问次数不用
一、联结后的表是什么样子?
原 SQL 中使用 order_tb m join visit_tb n on date(m.order_time)=date(n.visit_time)
,表示按 “日期” 关联两张表(即订单创建日期与访问日期相同)。以 2022-09-01 为例,关联后的表结构和部分数据如下:
关联逻辑:
- 左表
order_tb
是 2022-09-01 的订单(order_id=101、102、103)。 - 右表
visit_tb
是 2022-09-01 的访问记录(info_id=911、912、913、914)。 - 按 “日期相同” 关联后,每一条订单会与当天所有访问记录匹配,形成 “订单 - 访问” 的笛卡尔积组合(即订单数 × 访问数的行数)。
二、为什么两个 user_id 都要去重?
核心原因是:统计的是 “用户数” 而非 “记录数”,需排除同一用户的重复计算。
1. 对订单用户(m.user_id
)去重:count(distinct m.user_id)
- 同一用户当天可能下多个订单(如 2022-09-02 的 user_id=12 下了 2 个订单)。
- 若不去重,
count(m.user_id)
会统计为 “订单数”(如 12 会被算 2 次),但实际应统计为 “1 个下单用户”。 - 示例:2022-09-02 订单表中 user_id=12 有 2 条记录,去重后仅算 1 人。
2. 对访问用户(n.user_id
)去重:count(distinct n.user_id)
- 同一用户当天可能有多次访问(如 2022-09-02 的 user_id=11 有 2 次访问)。
- 若不去重,
count(n.user_id)
会统计为 “访问记录数”(如 11 会被算 2 次),但实际应统计为 “1 个访问用户”。 - 示例:2022-09-02 访问表中 user_id=11 有 2 条记录,去重后仅算 1 人。