Pandas 是 Python 資料分析的核心函式庫,提供豐富的資料操作工具。本文聚焦於聚合、轉換和對映三種關鍵技術,並結合程式碼範例,解析如何在不同資料結構上應用這些方法。同時也介紹了資料分箱的技巧,包含使用 pd.cut
進行分組和 pd.get_dummies
進行獨熱編碼,最後以流程圖形式總結了資料處理的完整步驟,方便讀者快速掌握 Pandas 資料處理的核心概念和實務操作。
Pandas 資料分析中的聚合、轉換與對映技術
在進行資料分析時,Pandas 函式庫提供了多種強大的工具來處理和轉換資料。本文將深入探討聚合(Aggregation)、轉換(Transformation)和對映(Mapping)這三種重要技術,並透過具體範例展示如何在實際資料分析中應用這些方法。
聚合操作
聚合操作是指將多個資料值合併成一個單一值的過程。在 Pandas 中,無論是 Series 還是 DataFrame,都支援多種聚合操作。
Series 聚合
對於 Series 而言,聚合操作相對簡單,因為只有一個維度需要考慮。我們可以直接呼叫如 sum
、mean
等方法來進行聚合。
import pandas as pd
import numpy as np
# 建立一個包含隨機數的 Series
np.random.seed(42)
ser = pd.Series(np.random.rand(10_000), dtype=pd.Float64Dtype())
# 計算平均值並加上 42
def mean_and_add_42(ser: pd.Series):
return ser.mean() + 42
# 使用 agg 方法進行聚合
result = ser.agg(mean_and_add_42)
print(result)
DataFrame 聚合
對於 DataFrame,聚合操作可以沿著不同的軸(axis)進行。預設情況下,聚合操作沿著列(axis=0)進行。
# 建立一個包含隨機數的 DataFrame
np.random.seed(42)
df = pd.DataFrame(np.random.randn(10_000, 6), columns=list("abcdef")).convert_dtypes(dtype_backend="numpy_nullable")
# 沿著列進行求和聚合
result_columns = df.sum()
print(result_columns)
# 沿著行進行求和聚合
result_rows = df.sum(axis=1)
print(result_rows)
同時進行多重聚合
使用 agg
方法,我們可以同時對資料進行多種聚合操作。
# 同時計算最小值和最大值
result = df.agg(["min", "max"])
print(result)
轉換操作
轉換操作與聚合操作不同,它們不會減少資料的維度,而是保持原始資料的形狀。
Series 轉換
對於 Series,我們可以使用 transform
方法來進行轉換操作。
# 建立一個簡單的 Series
ser = pd.Series([-1, 0, 1], dtype=pd.Int64Dtype())
# 定義一個轉換函式
def adds_one(ser: pd.Series) -> pd.Series:
return ser + 1
# 進行轉換操作
result = ser.transform(["abs", adds_one])
print(result)
DataFrame 轉換
同樣地,DataFrame 也可以使用 transform
方法進行轉換。
# 建立一個 DataFrame
df = pd.DataFrame(np.arange(-5, 4, 1).reshape(3, -1)).convert_dtypes(dtype_backend="numpy_nullable")
# 進行絕對值轉換
result_abs = df.transform("abs")
print(result_abs)
# 同時進行多種轉換
def add_42(ser: pd.Series):
return ser + 42
result_multiple = df.transform(["abs", add_42])
print(result_multiple)
對映操作
對映操作允許我們對資料中的每個元素單獨進行處理,這在處理混合型資料時特別有用。
對 Series 進行對映
# 建立一個混合型別的 Series
ser = pd.Series([123.45, [100, 113], 142.0, [110, 113, 119]])
# 定義一個自定義平均函式
def custom_average(value):
if isinstance(value, list):
return sum(value) / len(value)
return value
# 對 Series 中的每個元素進行對映
result = ser.map(custom_average)
print(result)
對 DataFrame 進行對映
同樣地,我們也可以對 DataFrame 中的每個元素進行對映。
# 建立一個混合型別的 DataFrame
df = pd.DataFrame([
[2., [1, 2], 3.],
[[4, 5], 5, 7.],
[1, 4, [1, 1, 5.5]],
])
# 對 DataFrame 中的每個元素進行對映
result = df.map(custom_average)
print(result)
視覺化流程圖
以下是一個簡單的流程圖,用於展示資料處理的基本步驟:
flowchart TD A[開始] --> B{檢查資料型別} B -->|數值型別| C[進行聚合操作] B -->|混合型別| D[進行對映操作] C --> E[結果輸出] D --> E
圖表翻譯:
此圖示展示了資料處理的基本流程。首先檢查資料的型別,如果是數值型別,則進行聚合操作;如果是混合型別,則進行對映操作。最後輸出處理結果。
資料分析中的分組與摘要統計
在資料分析過程中,經常需要對資料進行分組或計算摘要統計,以理解資料的基本特性和分佈情況。本章節將介紹 pandas 中幾個強大的方法,包括 pd.Series.value_counts
、pd.Series.describe
和 pd.cut
,這些方法能夠幫助分析師快速掌握資料的關鍵特徵。
摘要統計
摘要統計提供了一種快速瞭解資料基本屬性和分佈的方式。pandas 中的 pd.Series.value_counts
和 pd.Series.describe
方法是進行資料探索的強大工具。
使用 pd.Series.value_counts
pd.Series.value_counts
方法能夠計算每個不同資料點的頻率,對於離散型資料尤其有用。
# 建立一個包含字串的 Series
ser = pd.Series(["a", "b", "c", "a", "c", "a"], dtype=pd.StringDtype())
# 計算每個值的出現次數
ser.value_counts()
圖表說明:value_counts
流程
flowchart TD A[建立 Series] --> B{計算值次數} B --> C[輸出結果]
圖表翻譯:
此圖示展示了使用 value_counts
方法計算 Series 中各個值出現次數的流程。首先建立一個包含資料的 Series,然後呼叫 value_counts
方法,最後輸出結果。
使用 pd.Series.describe
對於連續型資料,pd.Series.describe
方法提供了一系列統計指標,包括計數、平均值、最小值和最大值等,能夠給出資料分佈的整體概覽。
# 建立一個包含整數的 Series
ser = pd.Series([0, 42, 84], dtype=pd.Int64Dtype())
# 計算並輸出描述性統計
ser.describe()
圖表說明:describe
流程
flowchart TD A[建立 Series] --> B{計算描述性統計} B --> C[輸出結果]
圖表翻譯:
此圖示展示了使用 describe
方法計算 Series 描述性統計的流程。首先建立一個包含資料的 Series,然後呼叫 describe
方法,最後輸出結果。
分箱演算法
分箱是將連續變數分類別到離散區間的過程,可以將無限多的值轉換為有限的「箱」以便於分析。
使用 pd.cut
進行分箱
假設我們有一份包含使用者年齡的調查資料,可以使用 pd.cut
將這些年齡分組到不同的年齡段。
# 建立一個包含使用者名稱和年齡的 DataFrame
df = pd.DataFrame([
["Jane", 34],
["John", 18],
["Jamie", 22],
["Jessica", 36],
["Jackie", 33],
["Steve", 40],
["Sam", 30],
["Stephanie", 66],
["Sarah", 55],
["Aaron", 22],
["Erin", 28],
["Elsa", 37],
], columns=["name", "age"])
# 將年齡分成 4 組
pd.cut(df["age"], 4)
圖表說明:pd.cut
分箱流程
flowchart TD A[建立 DataFrame] --> B{將年齡分組} B --> C[輸出分組結果]
圖表翻譯:
此圖示展示了使用 pd.cut
方法將年齡資料分箱的流程。首先建立一個包含使用者資料的 DataFrame,然後呼叫 pd.cut
方法將年齡分成指定數量的組別,最後輸出分組結果。
資料轉換方法:map
、transform
和 apply
在資料處理過程中,經常需要對資料進行轉換。pandas 提供了多種方法,如 map
、transform
和 apply
,用於不同的資料轉換需求。
map
方法
map
方法能夠對 Series 中的每個元素應用一個函式。
# 定義一個自定義平均值函式
def custom_average(value):
if isinstance(value, list):
return sum(value) / len(value)
return value
# 建立一個 Series 並應用自定義函式
ser = pd.Series([[1, 2], 3, [4, 5]])
ser.map(custom_average)
圖表說明:map
方法流程
flowchart TD A[建立 Series] --> B{應用自定義函式} B --> C[輸出結果]
圖表翻譯:
此圖示展示了使用 map
方法對 Series 中的每個元素應用自定義函式的流程。首先建立一個包含資料的 Series,然後呼叫 map
方法應用函式,最後輸出結果。
transform
方法
transform
方法與 map
類別似,但它適用於 DataFrame 時會對每一列進行操作。
# 對 DataFrame 的每一列應用自定義函式
df = pd.DataFrame({
'A': [1, 2, 3],
'B': [[4, 5], 6, 7]
})
df.transform(custom_average)
圖表說明:transform
方法流程
flowchart TD A[建立 DataFrame] --> B{對每一列應用函式} B --> C[輸出結果]
圖表翻譯:
此圖示展示了使用 transform
方法對 DataFrame 的每一列應用自定義函式的流程。首先建立一個包含資料的 DataFrame,然後呼叫 transform
方法應用函式,最後輸出結果。
apply
方法
apply
方法提供了更大的靈活性,可以對 Series 或 DataFrame 的元素或列應用函式。
# 對 Series 的每個元素應用除錯函式
def debug_apply(value):
print(f"Apply was called with value:\n{value}")
return value
ser = pd.Series([0, 1, 2], dtype=pd.Int64Dtype())
ser.apply(debug_apply)
圖表說明:apply
方法流程
flowchart TD A[建立 Series] --> B{對每個元素應用除錯函式} B --> C[輸出結果]
圖表翻譯:
此圖示展示了使用 apply
方法對 Series 的每個元素應用除錯函式的流程。首先建立一個包含資料的 Series,然後呼叫 apply
方法應用函式,最後輸出結果。
資料分箱技術詳解
在資料分析和機器學習領域中,資料分箱(Binning)是一種常見的資料預處理技術,用於將連續型資料轉換為離散型資料。本章節將深入探討使用pandas函式庫中的pd.cut
函式來實作資料分箱的方法。
使用pd.cut進行資料分箱
pd.cut
函式的主要功能是根據指定的區間範圍,將連續型資料切割成不同的類別。以下是一個簡單的範例:
import pandas as pd
# 建立範例資料
data = {'name': ['Jane', 'John', 'Jamie', 'Jessica', 'Jackie', 'Steve', 'Sam', 'Stephanie', 'Sarah', 'Aaron', 'Erin', 'Elsa'],
'age': [34, 18, 22, 36, 33, 40, 30, 66, 55, 22, 28, 37]}
df = pd.DataFrame(data)
# 使用pd.cut進行資料分箱
df['age_bin'] = pd.cut(df['age'], 4, precision=0)
print(df)
程式碼解析:
- 首先,我們建立了一個包含姓名和年齡的DataFrame。
- 使用
pd.cut
函式將年齡欄位分成4個區間。 precision=0
引數用於控制區間標籤的精確度,避免出現不必要的十進位數字。
自定義分箱區間
除了自動分箱外,pd.cut
還允許我們自定義分箱區間。以下是一個範例:
# 自定義分箱區間
bins = [10, 20, 30, 40, 50, 60, 999]
labels = ['10-20', '20-30', '30-40', '40-50', '50-60', '60+']
df['age_group'] = pd.cut(df['age'], bins=bins, labels=labels, right=False)
print(df)
程式碼解析:
- 定義了自定義的分箱區間
bins
和對應的標籤labels
。 - 使用
right=False
引數控制區間的包含性,實作左閉右開的區間劃分。 - 將自定義的分箱結果儲存在新的
age_group
欄位中。
獨熱編碼(One-Hot Encoding)
在資料分析和機器學習中,常常需要將類別型資料轉換為數值型資料。pd.get_dummies
函式提供了一種簡單的獨熱編碼方法。
# 建立範例Series
ser = pd.Series(["green", "brown", "blue", "amber", "hazel", "amber", "green", "blue", "green"], name="eye_colors", dtype=pd.StringDtype())
# 進行獨熱編碼
dummies = pd.get_dummies(ser, prefix='is')
print(dummies)
程式碼解析:
- 建立了一個包含類別型資料的Series。
- 使用
pd.get_dummies
函式進行獨熱編碼。 prefix='is'
引數用於自定義產生的欄位名稱字首。
資料處理流程最佳化
在進行資料處理時,合理的程式碼組織方式非常重要。pandas提供了.pipe
方法來實作方法鏈式呼叫,使程式碼更加簡潔和可讀。
# 使用.pipe方法進行鏈式呼叫
result = (df
.assign(age_bin=lambda x: pd.cut(x['age'], 4))
.pipe(lambda x: pd.get_dummies(x, columns=['age_bin'])))
print(result)
程式碼解析:
- 使用
.assign
方法新增了一個age_bin
欄位。 - 使用
.pipe
方法將DataFrame傳遞給pd.get_dummies
函式進行獨熱編碼。 - 整個處理流程透過方法鏈的方式實作,提高了程式碼的可讀性。
Mermaid流程圖展示資料處理流程
flowchart TD A[原始資料] --> B{資料預處理} B -->|連續型資料| C[使用pd.cut進行分箱] B -->|類別型資料| D[使用pd.get_dummies進行獨熱編碼] C --> E[資料分箱結果] D --> F[獨熱編碼結果] E --> G[最終資料集] F --> G
圖表解析:
此圖展示了資料處理的基本流程。首先,原始資料經過預處理階段。對於連續型資料,使用pd.cut
進行分箱處理;對於類別型資料,則使用pd.get_dummies
進行獨熱編碼。最終,處理後的資料被整合到最終的資料集中。這個流程清晰地展示了資料從原始狀態到可用狀態的轉換過程。