向前滾動累加SQL 實現思路

一、業務背景

在經營分析場景里,我們經常需要回答:

  • “截至今天,過去 N 天/月/周累計發生了多少?”

  • “把維度切到省、市、房型、項目經理、代理商等,結果又是什么?”

本文用兩個真實需求做演示:

  1. 以天為粒度,計算過去 7 天 的放款單量、放款金額;并順便給出過去 5 天 的口徑作為對比。

  2. 以月為粒度,計算過去 6 個月(含當月)的累計訂單數,維度為代理商。

為了便于閱讀,下文所有表名、字段名都做了脫敏混淆,但邏輯 100 % 保留。


二、需求 1:過去 7 天放款(天粒度,多維度)

2.1 期望輸出

data_date…(其它維度)loan_cntloan_amtys_fst_apply_cnt_7sumdelivery_go_capacity_sum

其中:

  • ys_fst_apply_cnt_7sum = 過去 7 天(不含當日)的同維度放款單量之和

  • delivery_go_capacity_sum = 過去 7 天(不含當日)的同維度放款金額之和

2.2 實現思路

采用 自關聯(self-join)

  • 主表 A:取當日維度切片;

  • 從表 B:在時間窗口 [A.data_date-7, A.data_date-1] 且維度完全一致的數據;

  • SUM() 聚合即可完成累加。

2.3 關鍵 SQL

SELECTa.data_date,a.dim_province,a.dim_city,a.dim_town,a.dim_roof1,a.dim_roof2,a.dim_pm,a.dim_dealer,a.dim_dealer_team,a.dim_settle,a.cnt_當天單量,a.amt_當天金額,/* 過去 7 天(不含當日)累計 */SUM(COALESCE(b.cnt_當天單量,0)) AS cnt_7d,SUM(COALESCE(b.amt_當天金額,0)) AS amt_7d,/* 過去 5 天(不含當日)累計,僅作演示 */SUM(CASE WHEN a.data_date - b.data_date <= 5 THEN COALESCE(b.cnt_當天單量,0) ELSE 0 END) AS cnt_5d,SUM(CASE WHEN a.data_date - b.data_date <= 5 THEN COALESCE(b.amt_當天金額,0) ELSE 0 END) AS amt_5d
FROM fact_daily_loan a
LEFT JOIN fact_daily_loan bON (COALESCE(a.dim_province,' ')   = COALESCE(b.dim_province,' ')AND COALESCE(a.dim_city,' ')       = COALESCE(b.dim_city,' ')AND COALESCE(a.dim_town,' ')       = COALESCE(b.dim_town,' ')AND COALESCE(a.dim_roof1,' ')      = COALESCE(b.dim_roof1,' ')AND COALESCE(a.dim_roof2,' ')      = COALESCE(b.dim_roof2,' ')AND COALESCE(a.dim_pm,' ')         = COALESCE(b.dim_pm,' ')AND COALESCE(a.dim_dealer,-1)      = COALESCE(b.dim_dealer,-1)AND COALESCE(a.dim_dealer_team,-1) = COALESCE(b.dim_dealer_team,-1)AND COALESCE(a.dim_settle,' ')     = COALESCE(b.dim_settle,' ')AND a.data_date - b.data_date BETWEEN 1 AND 7   -- 關鍵:滑窗 7 天
)
GROUP BYa.data_date,a.dim_province,a.dim_city,a.dim_town,a.dim_roof1,a.dim_roof2,a.dim_pm,a.dim_dealer,a.dim_dealer_team,a.dim_settle,a.cnt_當天單量,a.amt_當天金額;

2.4 注意點

  1. 維度對齊:所有維度都要 COALESCE 以防 NULL 匹配不上。

  2. 時間區間a.data_date - b.data_date BETWEEN 1 AND 7 等價于“前 7 天不含當日”。

  3. 性能:如果數據量大,建議把日期過濾下推、或在從表加索引 (date, 維度組合)


三、需求 2:過去 6 月訂單(月粒度,僅代理商維度)

3.1 期望輸出

report_monthdealer_namedealer_idcnt_6m

3.2 實現思路

采用 生成月份序列 + 預聚合 的經典寫法:

  1. 先把事實表出現的所有月份抽出來(去重)。

  2. 為每個月生成一個 6 個月窗口(含自己 + 前 5 個月)。

  3. 預先把訂單按月去重,得到 (dealer, month, order_no) 的干凈集合。

  4. 用窗口月把“干凈集合”掛上去,再 COUNT(DISTINCT order_no) 即可。

3.3 關鍵 SQL

-- 1. 提取事實表所有月份
WITH months AS (SELECT DISTINCT date_trunc('month', confirm_dt) AS month_startFROM fact_order_detail
),-- 2. 為每個月生成 6 個月窗口
windowed AS (SELECTm.month_start,generate_series(m.month_start - INTERVAL '5 month',m.month_start,INTERVAL '1 month')::date AS window_monthFROM months m
),-- 3. 預聚合:按月去重訂單
base AS (SELECTdealer_name,dealer_id,date_trunc('month', confirm_dt) AS month_start,order_noFROM fact_order_detail
),-- 4. 把窗口拼到 base 上
agg AS (SELECTw.month_start      AS report_month,b.dealer_name,b.dealer_id,COUNT(DISTINCT b.order_no) AS cnt_6mFROM windowed wJOIN base bON b.month_start = w.window_monthGROUP BYw.month_start,b.dealer_name,b.dealer_id
)-- 5. 最終輸出
SELECTcnt_6m,dealer_name,dealer_id,to_char(report_month, 'YYYY-MM-DD') AS report_month_str
FROM agg
ORDER BYdealer_id,report_month;

3.4 注意點

  • generate_series 生成月份序列,天然避開了閏月、大小月問題。

  • 預先把訂單按月去重,避免后面 COUNT DISTINCT 時掃大表。

  • 如果窗口更大(如 12 個月),可把 5 改成 11 即可。


四、兩種方案對比與選型建議

維度7 天放款(自關聯)6 月訂單(生成序列)
粒度
窗口7 天6 個月
維度多(省/市/房型…)少(僅代理商)
數據量百萬/千萬級千萬級
主要算子Self-Join + SUMgenerate_series + JOIN + COUNT DISTINCT
性能敏感點維度組合基數高導致笛卡爾放大月份序列膨脹有限,可接受
適用場景任意維度、短周期滾動累加維度單一、長周期滾動累加

一句話總結:

  • 短周期 + 高維度 → 自關聯 + 時間過濾;

  • 長周期 + 低維度 → 預聚合 + 生成序列。


五、擴展思考

  1. Presto/Trino 可用 RANGE BETWEEN INTERVAL '7' DAY PRECEDING AND 1 DAY PRECEDING 的窗口函數,邏輯更簡潔,但引擎需要支持。

  2. ClickHouse 可用 GROUP BY (date, dim...) WITH ROLLUP + runningAccumulate 實現實時累加。

  3. 實時場景 可以把窗口結果寫到 Redis / Druid,再通過 API 提供毫秒級查詢。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/90645.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/90645.shtml
英文地址,請注明出處:http://en.pswp.cn/web/90645.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Spring AI(14)——文本分塊優化

RAG時&#xff0c;檢索效果的優劣&#xff0c;和文本的分塊的情況有很大關系。SpringAI中通過TokenTextSplitter對文本分塊。本文對SpringAI提供的TokenTextSplitter源碼進行了分析&#xff0c;并給出一些自己的想法&#xff0c;歡迎大家互相探討。查看了TokenTextSplitter的源…

Python----大模型(RAG 的智能評估-LangSmith)

一、LangSmith LangSmith是LangChain的一個子產品&#xff0c;是一個大模型應用開發平臺。它提供了從原 型到生產的全流程工具和服務&#xff0c;幫助開發者構建、測試、評估和監控基于LangChain 或其他 LLM 框架的應用程序。 安裝 LangSmith pip install langsmith0.1.137 官網…

磁懸浮軸承轉子不平衡質量控制策略設計:原理、分析與智能實現

磁懸浮軸承(Active Magnetic Bearing, AMB)以其無接觸、無摩擦、高轉速、無需潤滑等革命性優勢,在高端旋轉機械領域(如高速電機、離心壓縮機、飛輪儲能、航空航天動力系統)展現出巨大潛力。然而,轉子固有的質量不平衡是AMB系統面臨的核心挑戰之一,它誘發強同步振動,威脅…

C++查詢mysql數據

文章目錄 文章目錄 1.前言 2. 代碼 &#xff08;1&#xff09;執行查詢SQL &#xff08;2&#xff09;獲取結果集 &#xff08;3&#xff09;遍歷結果集&#xff08;獲取字段數、行數&#xff09; &#xff08;4&#xff09;釋放資源 3.完整代碼 1.前言 我們成功連接數…

【論文閱讀】-《GenAttack: Practical Black-box Attacks with Gradient-Free Optimization》

GenAttack&#xff1a;利用無梯度優化的實用黑盒攻擊 Moustafa Alzantot UCLA Los Angeles, U.S.A malzantotucla.edu Yash Sharma Cooper Union New York, U.S.A sharma2cooper.edu Supriyo Chakraborty IBM Research New York, U.S.A supriyous.ibm.com Huan Zhang UCLA Los…

CT、IT、ICT 和 DICT區別

這四個術語&#xff1a;CT、IT、ICT 和 DICT&#xff0c;是信息通信行業中常見的核心概念&#xff0c;它們既有演進關系&#xff0c;又有各自的技術重點。&#x1f539; 一、CT&#xff08;Communication Technology&#xff09;通信技術**定義&#xff1a;**以語音通信為核心的…

Effective C++ 條款4:確定對象被使用前已先被初始化

Effective C 條款4&#xff1a;確定對象被使用前已先被初始化核心思想&#xff1a;永遠在使用對象前將其初始化。未初始化對象是未定義行為的常見來源&#xff0c;尤其對于內置類型。 1. 內置類型手動初始化 int x 0; // 手動初始化 const char* text &quo…

LangSmith的配置介紹

文章目錄注冊及登錄生成API KeyLangSmith的配置方式一&#xff1a;放運行環境里方式二&#xff1a;寫代碼里執行代碼查看LangSmith上是否看到本次運行的項目記錄LangSmith的其他注意注冊及登錄 首先使用郵箱注冊一個賬號及設置密碼&#xff0c;等收到收到郵件后&#xff0c;進…

Linux的生態與軟件安裝

堅持用 清晰易懂的圖解 代碼語言&#xff0c;讓每個知識點變得簡單&#xff01; &#x1f680;呆頭個人主頁詳情 &#x1f331; 呆頭個人Gitee代碼倉庫 &#x1f4cc; 呆頭詳細專欄系列 座右銘&#xff1a; “不患無位&#xff0c;患所以立。” Linux的生態與軟件安裝前言目錄…

3.4 安全-分布式-數據庫-挖掘

一、數據庫的安全數據庫里面的安全措施&#xff1a;用戶標識和鑒定&#xff1a;用戶的賬戶口令等存取控制&#xff1a;對用戶操作進行控權&#xff0c;有對應權限碼才能操作。密碼存儲和傳輸&#xff1a;加密存儲。視圖的保護&#xff1a;視圖需要授權審計&#xff1a;專門的文…

多線程 Reactor 模式

目錄 多線程 Reactor 模式的核心動機 多線程演進方向 多線程 Reactor 模型結構 多線程 EchoServer 實現核心部分 Handler 的多線程化 多線程 Reactor 的三個核心點 本篇文章內容的前置知識為 單線程 Reactor 模式&#xff0c;如果不了解&#xff0c;可點擊鏈接學習 單線程…

[NLP]多電源域設計的仿真驗證方法

多電源域設計的仿真驗證方法 1. 更復雜的 Testbench 例子(多電源域、復雜低功耗場景) 假設有兩個電源域 PD1 和 PD2,分別對應控制信號 pwr_sw_ctrl1、iso_ctrl1、ret_ctrl1 和 pwr_sw_ctrl2、iso_ctrl2、ret_ctrl2,且兩域之間有通信。 RTL 端口聲明(簡化版) module top…

Apache Ignite 中 WHERE 子句中的子查詢(Subqueries in WHERE Clause)的執行方式

這段內容是關于 Apache Ignite 中 WHERE 子句中的子查詢&#xff08;Subqueries in WHERE Clause&#xff09;的執行方式 的說明。理解這段內容對于編寫高效的 SQL 查詢、避免性能瓶頸非常重要。下面我將為你 逐句解釋并深入理解這段內容。&#x1f9fe; 原文翻譯 解釋 原文&a…

MySQL(153)如何使用全文索引?

MySQL的全文索引&#xff08;Full-Text Index&#xff09;是一種特殊的索引類型&#xff0c;專門用于加速文本數據的搜索。與普通的B樹索引不同&#xff0c;全文索引適用于大文本字段&#xff08;如TEXT、VARCHAR等&#xff09;的全文搜索。它通過構建一個倒排索引&#xff0c;…

微分方程入門之入門之入門,純筆記

當描述 相對變化量 比 絕對量 更容易時&#xff0c;微分方程就經常用到了。 比如&#xff0c;描述為什么種群數量增加or減少【相對】&#xff0c;比描述為什么它在某個時間點是某個特定值【絕對】更容易。 物理學中&#xff0c;運動經常用力來描述&#xff0c;力–>代表變化…

【C++】簡單學——vector類(模擬實現)

模擬實現的準備工作 看源碼&#xff0c;了解這個類的大概組成 1.先看成員變量 成員變量的組成是三個迭代器 問&#xff1a;這個iterator內嵌類型究竟是什么&#xff1f;即這個迭代器是什么 迭代器實際就是T* 問&#xff1a;這三個迭代器代表什么意思&#xff1f; 連蒙帶猜…

【WRF】根據自動安裝腳本安裝 WRF / WRF-CHEM等

目錄 GitHub 上 WRF 自動安裝腳本 ?? 腳本的作用 ??? 支持的系統 ?? 可安裝的 WRF 版本及其選項 ? 如何使用(以 WRF 4.6.1 為例) ? 依賴庫的安裝位置 完整安裝腳本分析 參考 GitHub 上 WRF 自動安裝腳本 GitHub 上的 WRF-Install-Script 項目的 Releases(發布版本…

M2IV:面向大型視覺-語言模型中高效且細粒度的多模態上下文學習

MIV&#xff1a; Towards Efficient and Fine-grained Multimodal In Context Learning in Large Vision-Language Models COLM 2025 why 新興的研究方向&#xff1a;上下文學習&#xff08;ICL&#xff09;的效果“向量化”&#xff0c;其核心思想是用transformer內部的向量來…

龍迅#LT8711UXD適用于Type-C/DP1.4 /EDP轉 HDMI2.0 功能,分辨率高達4K60HZ,可支持HDCP!

1. 描述LT8711UXD 是一款高性能雙通道 Type-C/DP1.4 轉 HDMI2.0 轉換器&#xff0c;旨在將 USB Type-C 源或 DP1.4 源連接到 HDMI2.0 接收器。該LT8711UXD集成了一個符合 DP1.4 標準的接收器和一個符合 HDMI2.0 標準的發射器。此外&#xff0c;還嵌入了兩個用于CC通信的CC控制器…

《計算機組成原理與匯編語言程序設計》實驗報告一 基本數字邏輯及漢字顯示

目 錄 一、實驗學時 二、實驗目的 三、實驗要求 四、實驗內容 五、實驗步驟 1、打開Logisim軟件&#xff0c;列出異或邏輯電路真值表&#xff0c;并使用與、或、非基本原件實現異或邏輯電路。 2、打開Logisim軟件&#xff0c;列出同或邏輯電路真值表&#xff0c;并使用…