You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

MySQL/Presto替代union all实现循环统计2021年起每月初持卡用户数

优化SQL实现方案:按月统计月初有效用户数

核心思路

  • 第一步:生成2021-01-01到当前月的所有月初日期连续序列,替代手动写死的单月日期
  • 第二步:将日期序列和用户开卡表做条件关联,过滤出每个月初对应的有效用户(匹配你原有的时间判断规则:开卡时间<=月初,到期时间>=月初+1天)
  • 第三步:按国家、年月分组统计去重用户数即可,无需重复编写union all语句

Presto 语法版本

WITH month_list AS (
    -- 生成2021-01-01到当前月的月初日期数组
    SELECT sequence(
        DATE '2021-01-01',
        DATE_TRUNC('month', CURRENT_DATE),
        INTERVAL '1' MONTH
    ) AS month_arr
),
-- 把数组拆解为每行一个月初日期
stat_dates AS (
    SELECT month_start
    FROM month_list
    CROSS JOIN UNNEST(month_arr) AS t(month_start)
)
SELECT
    COALESCE(s.country_id, 1) AS country_id,
    YEAR(stat_dates.month_start) AS year,
    MONTH(stat_dates.month_start) AS month,
    COUNT(DISTINCT s.user) AS total_members
FROM stat_dates
LEFT JOIN your_table s
    ON DATE(CAST(s.start_at AS TIMESTAMP)) <= stat_dates.month_start
    AND DATE(CAST(s.end_at AS TIMESTAMP)) >= DATE_ADD('day', 1, stat_dates.month_start)
GROUP BY 1,2,3
ORDER BY year DESC, month DESC;

MySQL 8.0+ 语法版本

WITH RECURSIVE stat_dates AS (
    -- 统计起始月初
    SELECT DATE('2021-01-01') AS month_start
    UNION ALL
    -- 递归生成后续月份月初,直到当前月
    SELECT DATE_ADD(month_start, INTERVAL 1 MONTH)
    FROM stat_dates
    WHERE month_start < DATE_FORMAT(CURRENT_DATE, '%Y-%m-01')
)
SELECT
    COALESCE(s.country_id, 1) AS country_id,
    YEAR(stat_dates.month_start) AS year,
    MONTH(stat_dates.month_start) AS month,
    COUNT(DISTINCT s.user) AS total_members
FROM stat_dates
LEFT JOIN your_table s
    ON DATE(CAST(s.start_at AS DATETIME)) <= stat_dates.month_start
    AND DATE(CAST(s.end_at AS DATETIME)) >= DATE_ADD(stat_dates.month_start, INTERVAL 1 DAY)
GROUP BY 1,2,3
ORDER BY year DESC, month DESC;

注意事项

  • 替换代码中的your_table为你的实际表名即可直接使用,原有业务逻辑完全保留
  • 如需调整统计的起止时间,仅修改CTE部分的日期参数即可,无需新增union语句
  • 低于8.0的MySQL版本不支持递归CTE,可手动创建一张存储所有待统计月初日期的临时表,替代stat_dates部分的逻辑

内容的提问来源于stack exchange,提问作者Mukesh Marimuthu

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.23 22:45:06