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

如何使用PostgreSQL计算距离当前日期的连续天数?

Postgres SQL 计算距当前日期连续活跃天数方案

问题根源

原有SQL的计算偏差来自同一用户同一天存在多条watch_history记录时,行号会重复计数,导致连续日期分组逻辑失效,你需要的created_at去重逻辑可以通过提前按用户+日期维度去重实现。

修正后完整SQL(适配到当前日期的连续天数统计)

WITH unique_dates AS (
    -- 先按用户+日期去重,确保每个用户每天仅保留一条记录,实现你要的created_at去重需求
    SELECT DISTINCT user_id, created_at::timestamp::date AS visit_date
    FROM watch_history
    -- 若要查询特定用户比如示例中的702,可在此处加过滤条件:WHERE user_id = 702
),
grouped_dates AS (
    SELECT 
        user_id,
        visit_date,
        -- 经典连续日期分组逻辑:连续日期减去对应行号会得到相同的分组值
        visit_date - (ROW_NUMBER() OVER (PARTITION BY user_id ORDER BY visit_date) || ' days')::interval::date AS grouping_date
    FROM unique_dates
)
-- 统计每个用户到当前日期的最新连续天数
SELECT 
    user_id,
    COUNT(*) AS current_consecutive_days
FROM grouped_dates
WHERE grouping_date = CURRENT_DATE - COUNT(*) OVER (PARTITION BY user_id, grouping_date)::integer
GROUP BY user_id, grouping_date
ORDER BY user_id;

全量连续周期统计简化版本

如果你只需要统计每个用户所有历史连续周期的天数,不需要限定到当前日期,用下方版本即可:

WITH unique_dates AS (
    SELECT DISTINCT user_id, created_at::timestamp::date AS visit_date
    FROM watch_history
),
grouped_dates AS (
    SELECT 
        user_id,
        visit_date,
        visit_date - (ROW_NUMBER() OVER (PARTITION BY user_id ORDER BY visit_date) || ' days')::interval::date AS grouping_date
    FROM unique_dates
)
SELECT 
    user_id,
    COUNT(*) AS number_of_consecutive_days,
    MIN(visit_date) AS streak_start_date,
    MAX(visit_date) AS streak_end_date
FROM grouped_dates
GROUP BY user_id, grouping_date
ORDER BY user_id, streak_end_date DESC;

内容的提问来源于stack exchange,提问作者Parth Shah

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.23 21:24:01