Pandas 簡介
Pandas
是一個開源的,BSD許可的庫,爲Python編程語言提供高性能,易於使用的數據結構和數據分析工具。
Pandas
是NumFOCUS贊助的項目。這將有助於確保Pandas成爲世界級開源項目的成功,並有可能捐贈給該項目。
安裝
pip install Pandas
必要包
import Pandas as pd
import numpy as np
基本用法
數據生成
Series
Series 和 list 類似,可以直接從 list 轉化
l = [i for i in range(5)]
l.append("Test")
s = pd.Series(l)
print(s)
0 0
1 1
2 2
3 3
4 4
5 Test
dtype: object
DataFrame
DataFrame 和python當中的 dict 類似,也可以直接從 dict 轉換,或者按照類似的規則生成。
需要特別注意 “索引” 和 “屬性” 的概念,如果對比矩陣的概念
- 索引:相當於矩陣當中的行號
- 屬性:相當於矩陣當中的列號
字典
所有 key 所對應的列表最長長度爲 4,它規定了整個DF的屬性(colums)長度,其餘 values 長度只能等於 4 或者 1
source = {
"A": [1, 2, 3],
"B": "test",
}
df = pd.DataFrame(source)
print(df)
A B
0 1 test
1 2 test
2 3 test
Series
# 索引
row = pd.date_range("20200601", periods=7)
# 屬性
col = ["A", "B", "C", "D", "E"]
# DF
df = pd.DataFrame(np.random.randint(6, size=(7, 5)), index=row, columns=col)
print(df)
A B C D E
2020-06-01 1 0 0 0 4
2020-06-02 0 5 5 4 2
2020-06-03 1 3 1 3 5
2020-06-04 0 0 2 1 1
2020-06-05 5 2 0 3 1
2020-06-06 5 2 4 2 2
2020-06-07 4 5 1 0 0
Series字典
所有 key 所對應的列表最長長度爲 4,它規定了整個DF的屬性(colums)長度,其餘 values 長度只能等於 4 或者 1
source = {
'A': 1,
'B': pd.Timestamp('20130102'),
'C': pd.Series(1, index=list(range(4)), dtype='float32'),
'D': np.array([3] * 4, dtype='int32'),
'E': pd.Categorical(["test", "train", "test", "train"]),
'F': 'foo',
}
df = pd.DataFrame(source)
print(df)
A B C D E F
0 1 2013-01-02 1.0 3 test foo
1 1 2013-01-02 1.0 3 train foo
2 1 2013-01-02 1.0 3 test foo
3 1 2013-01-02 1.0 3 train foo
數據導入
EXCEL
df = pd.read_excel("./EXCEL/pd_test.xlsx", sheet_name=0)
print(df.head())
序號 物資編碼 *物資描述 *單位 *數量 行控制價 附註
0 1 LB019009 維修服;夏;2011款 套 1222 3 11962一號線
1 2 LB019010 維修服;冬;2011款 套 1223 4 11962一號線
2 3 LB019010 維修服;冬;2011款 套 1224 5 11967二號線
3 4 LB019009 維修服;夏;2011款 套 1225 6 11967二號線
4 5 LB019010 維修服;冬;2011款 套 1226 7 12704三號線
數據導出
EXCEL
sheet_name
可以不填,默認Sheet1
sheet_name
值不能等於整數,必須爲字符串
df.to_excel("./EXCEL/pd_out.xlsx", sheet_name="Sheet0")
數據清洗
# 數據清洗
df = df.fillna(0)
分組
案例1:excel表格多行合一
要求
領導要求將表格簡化一下,主要有3點要求:
- 多個相同的物資編碼、物資描述統一爲一個
- 統計每個物資的數量
- 所有附註內容相加
思路
根據要求,設計如下處理思路:
- 以《物資編碼》《物資描述》《單位》《行控制價》爲索引,統計數量
- 以《物資編碼》《物資描述》《單位》《行控制價》爲索引,統計《附註》
- 以《物資編碼》《物資描述》《單位》《行控制價》爲鍵值,組合上面兩個表
代碼
import pandas as pd
import numpy as np
df = pd.read_excel("./EXCEL/pd_test.xlsx", sheet_name=0)
# ['序號', '物資編碼', '*物資描述', '*單位', '*數量', '行控制價', '附註']
# 數據清洗
df = df.fillna(0)
# 以《物資編碼》《物資描述》《單位》《行控制價》爲索引,統計《數量》
df_num = df.groupby(['物資編碼', '*物資描述', '*單位', '行控制價'])['*數量'].apply(np.sum)
# 以《物資編碼》《物資描述》《單位》《行控制價》爲索引,統計《附註》
df_commt = df.groupby(['物資編碼', '*物資描述', '*單位', '行控制價'])['附註'].apply(lambda df: "\n".join(df.values))
# 以《物資編碼》《物資描述》《單位》《行控制價》爲鍵值,組合上面兩個表
df_sum = pd.merge(df_num, df_commt, on=['物資編碼', '*物資描述', '*單位', '行控制價']).reset_index(drop=False)
# 重構《序號》
df_sum["序號"] = df_sum.index
df_sum.set_index("序號", inplace=True)
# 輸出excel
print(df_sum)
df_sum.to_excel("./EXCEL/pd_out.xlsx", sheet_name="Sheet0")
物資編碼 *物資描述 *單位 行控制價 *數量 附註
序號
0 LB019009 維修服;夏;2011款 套 0.0 12174 11962一號線\n11967二號線\n12704三號線\n11974三大修\n11966三...
1 LB019010 維修服;冬;2011款 套 0.0 12193 11962一號線\n11967二號線\n12704三號線\n11974三大修\n11966三...
效果圖
踩過的坑
不要看只是小小几行代碼,其中知識點還是挺多的:
- 處理表格前需要進行數據清理,否者會報錯
- 靈活使用lambda函數
- 如果想要保持表格的屬性(列)不變,則還需要重構序號,以及重新設定索引
案例2:多級分組
# 單層分組
gp1 = df.groupby(["物資編碼"])
# 所有組信息
print(gp1.groups)
# 迭代
for name, data in gp1:
print(name)
print(data)