2026年11月1日 星期日

【PySpark 大數據處理 07】進階資料清洗:字串處理 (String) 與時間格式 (Timestamp) 正規化

在上一篇中,我們成功消滅了缺失值與重複資料。但資料的考驗還沒結束!在真實的商業環境中,資料往往是由不同系統或人工輸入匯集而成的,這會導致兩個常見的災難:充滿雜訊的字串(例如多餘的空白、大小寫不一致),以及格式五花八門的日期時間。

今天,我們將學習 PySpark 內建強大的字串處理函數,以及如何將混亂的時間統一「正規化 (Normalization)」,為未來的時間序列分析打下良好基礎。

1. 觀念解析:為什麼需要正規化?

對電腦來說,字串 `"Apple "` (後面多一個空白) 和 `"Apple"` 是完全不同的東西;同樣地,字串 `"2026/10/25"` 與時間戳記 `2026-10-25 00:00:00` 在底層的處理邏輯也天差地遠。請參考下方的轉換示意圖:

字串與時間正規化流程 【情境一】字串除錯與清理 " TPCU_MIS " 多餘空白與大寫 trim() 去除空白 lower() 轉小寫 "tpcu_mis" 乾淨的標準字串 【情境二】時間格式正規化 "2026/10/25 14:49" 字串型態 (String) to_timestamp() 解析 "yyyy/MM/dd HH:mm" 2026-10-25 14:49:00 時間型態 (Timestamp)
▲ PySpark 字串清理與時間格式轉換示意圖

2. 字串大掃除:trim, lower 與 regexp_replace

我們首先匯入需要用到的內建函數。最常見的處理包含:去除首尾空白 trim()、統一轉小寫 lower(),或是利用正規表示式 (Regex) 替換掉不需要的字元。

from pyspark.sql.functions import col, trim, lower, regexp_replace

# 1. 去除首尾的多餘空白,並將字串統一轉為小寫
df_clean_str = df.withColumn("User_ID", lower(trim(col("User_ID"))))

# 2. 進階替換:把商品名稱中所有的「特殊符號(例如 #, @, !)」清除
# 使用正則表示式 [^\w\s] 代表保留字母、數字與空白,其餘替換為空字串
df_clean_str = df_clean_str.withColumn(
    "Product_Name", 
    regexp_replace(col("Product_Name"), r"[^\w\s]", "")
)

3. 時間的魔法:to_timestamp 與 date_format

當我們從 CSV 或 JSON 讀取資料時,日期往往只是普通的字串(例如 `"2026/10/25"`)。必須將它們轉換為 Spark 原生的 TimestampType,我們才能輕易地計算「這個月總銷量」或是「前後兩筆紀錄的時間差」。

from pyspark.sql.functions import to_timestamp, date_format

# 1. 將自訂格式的字串轉換為正規時間戳記
# 假設原始字串格式為 "2026/10/25 14:49"
df_time = df.withColumn(
    "Event_Time", 
    to_timestamp(col("Raw_Time_String"), "yyyy/MM/dd HH:mm")
)

# 2. 從標準時間中,萃取出特定的格式 (例如:只取 年-月)
# 這在做月度營收報表分組 (GroupBy) 時非常有用
df_time = df_time.withColumn(
    "Year_Month", 
    date_format(col("Event_Time"), "yyyy-MM")
)

df_time.select("Raw_Time_String", "Event_Time", "Year_Month").show(5)

4. 課後小結

掌握了字串與時間的正規化後,你的資料已經變得非常乾淨且具備結構化了!這意味著我們終於可以進入數據分析最迷人的階段。下一篇文章,我們將學習如何運用「群組運算 (GroupBy)」與「多維度聚合 (Aggregation)」,讓冰冷的數據開口說出有價值的商業洞察!

沒有留言:

張貼留言

熱門文章