CodeGym /課程 /SQL SELF /用 SQL 窗口函數做資料分析的範例

用 SQL 窗口函數做資料分析的範例

SQL SELF
等級 30 , 課堂 1
開放

現在你已經準備好要跳進實戰範例的世界,來看看這些東西在真實任務裡怎麼用啦!

範例:依地區計算銷售排名

假設我們有一張 sales 表,裡面有不同地區的銷售資料。我們要幫每個地區算出銷售排名。

id region sales_amount
1 North 5000
2 North 3000
3 North 7000
4 South 2000
5 South 4000
6 East 8000
7 East 6000

任務:找出每個地區的銷售排名 (RANK)

SELECT
    region,
    sales_amount,
    RANK() OVER (PARTITION BY region ORDER BY sales_amount DESC) AS sales_rank
FROM 
    sales;

結果:

region sales_amount sales_rank
North 7000 1
North 5000 2
North 3000 3
South 4000 1
South 2000 2
East 8000 1
East 6000 2

注意我們用了 PARTITION BY region,這樣排名才會分地區算。如果沒用 PARTITION BY,排名就會是全表一起比。

範例:計算每個客戶的累積收入

現在來處理 transactions 表,幫每個客戶算出累積(累加)收入。

id customer_id purchase_date amount
1 101 2023-01-01 100
2 101 2023-01-03 50
3 102 2023-01-02 200
4 101 2023-01-05 150
5 102 2023-01-04 100

任務:幫每個客戶算累積總和

SELECT
    customer_id,
    purchase_date,
    amount,
    SUM(amount) OVER (PARTITION BY customer_id ORDER BY purchase_date) AS cumulative_sum
FROM 
    transactions;

結果:

customer_id purchase_date amount cumulative_sum
101 2023-01-01 100 100
101 2023-01-03 50 150
101 2023-01-05 150 300
102 2023-01-02 200 200
102 2023-01-04 100 300

這裡重點是 OVER() 裡面有 ORDER BY purchase_date,這樣累積總和才會照時間順序算。

範例:把資料分成分位數

假設我們有一張 students 表,裡面有名字跟測驗分數。我們想要把學生依成績分成 4 組。

id name test_score
1 Alice 85
2 Bob 95
3 Charlie 75
4 Diana 88
5 Edward 65
6 Fiona 70

任務:用 NTILE() 把學生分成 4 組

SELECT
    name,
    test_score,
    NTILE(4) OVER (ORDER BY test_score DESC) AS quartile
FROM 
    students;

查詢結果會長這樣:

name test_score quartile
Bob 95 1
Diana 88 1
Alice 85 2
Charlie 75 3
Fiona 70 3
Edward 65 4

NTILE(4) 會把資料分成 4 組。分數最高的學生在第一組,最低的在最後一組。

範例:時序資料分析

site_visits 表裡有每天網站的訪問數。我們要算出每個網站每天訪問數的變化。

site_id visit_date visits
1 2023-01-01 100
1 2023-01-02 120
1 2023-01-03 110
2 2023-01-01 50
2 2023-01-02 60
2 2023-01-03 70

我們的任務 — 算出每天訪問數的變化

SELECT
    site_id,
    visit_date,
    visits,
    visits - LAG(visits) OVER (PARTITION BY site_id ORDER BY visit_date) AS visit_diff
FROM 
    site_visits;

結果:

site_id visit_date visits visit_diff
1 2023-01-01 100 NULL
1 2023-01-02 120 20
1 2023-01-03 110 -10
2 2023-01-01 50 NULL
2 2023-01-02 60 10
2 2023-01-03 70 10

LAG() 這個函數可以拿到前一列的值。如果沒有前一列,結果就會是 NULL。更多細節我們之後的課會再聊 :P

留言
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION