[Python] Pandas資料處理- 基本概念及操作

前言

Pandas是python的一個數據分析的函式庫,提供簡易使用的資料格式,使用者透過這項工具快速操作及分析資料,提供十分容易操作的資料結構如:DataFrame
Pandas不但可以網頁中的表格資料,還能從外部匯入資料,將這些資料進行排序、修改或是做成統計相關的圖表。

安裝 Pandas

1
pip install pandas  

Pandas資料結構

  • Series
    是一維陣列的資料結構,能夠保存不同資料的型態,如:整數、字串、浮點數。
  • DataFrame
    是一個二維陣列的資料結構,可以操作某行/列,或是多行/列的資料,也可以做排序、插入、修改或刪除等操作。

DataFrame 是常用資料處理的格式,尤其是在做報表處理的時候非常方便。

Series基本操作

建立Series

Series可以處理一維資料的型態包含陣列(array)、字典(dictionary)、單一資料。

資料為陣列(array)時

1
2
3
4
5
6
import pandas as pd 

cars = ["高雄", "花蓮", "台東", "台北", "台中"]

select = pd.Series(cars)
print(select)

資料為字典(dictionary)時

1
2
3
4
5
6
7
8
9
10
11
12
import pandas as pd

seri = {
"col0": "0",
"col1": "1",
"col2": "2",
"col3": "3",
"col4": "4",

}
seris = pd.Series(seri)
seris

取值

透過索引值或key名,篩選出目標值

1
2
3
4
5
6
7
8
print(seris[1]) # 依照索引值取單一值
print("--------")
print(seris["col2"]) # 依照key名稱取單一值
print("--------")
print(seris[[0, 2, 4]]) # 依照索引值取多個值
print("--------")
print(seris[["col1", "col3", "col4"]]) # 依照key名稱取多個值
print("--------")

透過索引值或key名,篩選出目標值

透過切片(slice)的方式進行索引值或key名,分割出目標值的範圍。

1
2
3
print(seris[:3]) # slice方法依照索引值選取目標範圍
print("--------")
print(seris[:"col3"]) # slice方法依照"key"名稱選取目標範圍

資料為資料為單一資料時

1
2
3
4
5
6
7
8
9
10
11
12
13
import pandas as pd

student = "Tom"
ser = pd.Series(student, index = range(3))
print(ser)

"""
結果
0 Tom
1 Tom
2 Tom
dtype: object
"""

DataFrame基本操作

建立DataFrame

資料為陣列(array)時

1
2
3
4
5
6
import pandas as pd

students = [["A", "male"],["B", "female"], ["C", "male"]]

df = pd.DataFrame(students, columns = ["name", "gender"]) # 指定欄位名稱
df

資料為字典(dictionary)時

1
2
3
4
5
6
7
8
9
10
11
import pandas as pd

students = {
"name": ["A","B", "C"],
"stid": [1,2, 3],
"gender": ["male","female", "male"],
"age": [20, 30, 40],
"city": ["高雄", "台北", "台中"]
}
df = pd.DataFrame(students)
df

讀取資料

pandas支援的資料格式很多種,常見的格式包含:

  • read_csv() 讀取*.csv格式的檔案
  • read_html() 讀取*.heml格式的檔案
  • read_sql() 讀取*.csv格式的檔案
  • read_excel() 讀取*.xlsx格式的檔案
  • read_json() 讀取*.json格式的檔案

寫入資料

  • to_csv() 讀取*.csv格式的檔案
  • to_html() 讀取*.heml格式的檔案
  • to_sql() 讀取*.csv格式的檔案
  • to_excel() 讀取*.xlsx格式的檔案
  • to_json() 讀取*.json格式的檔案

說明

  • encoding="utf-8-sig": 將BOM去除的utf-8編碼
  • index_col=0: 去除索引欄位

寫入資料範例(*.csv為例)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
import pandas as pd
scores = [
[60, 70, 80], [90, 66, 50], [47, 50, 88]
]
students = [
"student1", "student2", "student3"
]
subjects = [
"國", "英", "數"
]
df = pd.DataFrame(scores, columns=subjects, index=students )
print(df)

df.to_csv("scores.csv", encoding="utf-8-sig")

讀取資料範例

1
2
3
4
5
import pandas as pd
# 讀檔
data = pd.read_csv("scores.csv", encoding="utf-8-sig", index_col=0)

data.head()

讀取線.csv

透過正確的URL就可以讀取網路上的任意.csv檔案轉成DataFrame。

1
2
df = pd.read_csv('http://bit.ly/kaggletrain')
df.head()

顯示前5筆資料

df.head(): 使用.head()可以顯示資料,(預設5筆),當然也能自訂,只需要內加上要顯示資料的筆數

顯示最後一筆
df.head(1)

顯示後5筆資料

df.tail():
要顯示最後五筆資料則可以使用df.tail(),和df.head()一樣,可以在括號內加上要顯示資料的筆數

資料資訊

使用df.info()可以看到該檔案資訊

知道檔案的大小

回傳訊息為:顯示(rows,columns)

篩選資料

選擇一項資料

df["欄位名稱"]
假設我們想要選擇某個科目的欄位所有資料,以英文為例

1
df["英"]

選擇某幾筆資料

假設我們要前兩筆英文科目的成績資料

1
df["英"][:2]

選擇多項資料

要擴增選擇的欄位很簡單,用一個list的資料結構即可完成。
df[['欄位名稱','欄位名稱']]
以取得英文、數學這兩格欄位為例

1
df[["英", "數"]].head()

loc["x_label", "y_label"]

loc["x_label", "y_label"]基於行(column)和列(row)進行資料篩選,x_label表示列(row)的篩選,而y_label則是基於行(column)。

範例

原始資料:

針對student1至student3及國文英文科進行篩選,採用切片(slice)的方式。

1
2
# 用index的標籤來篩選出資料 concat_df
concat_df.loc["student1":"student3", :"英"]

iloc[]

基於行和列的索引值進行篩選,索引值都是從0開始。

範例

篩選列(row)的前五筆及行(column)的前兩筆

1
2
# 用index位置來篩選出資料
concat_df.iloc[:5, :2]

運算子篩選資料

除了上述方法外,pandas也可以利用運算子的方式來篩選條件,如條件運算的:== !=> <>= <=

範例

假設要篩選出英文分數>70分的學生

1
2
# 運算子篩選資料
concat_df["英"] > 70

執行範例程式碼後可看到回傳條件顯示TrueFalse,接著以TrueFalse當作篩選條件

1
2
condition = (concat_df["英"]  > 70)
concat_df[condition]

多個運算子篩選資料

如果過濾條件不只一個,布林運算子就派上用場了!

範例

篩選出國等於80分、數學大於60分、英文大於70分的學生,三個條件都須符合的話用and運算,或是&符號。

1
2
3
4
condition1 = (concat_df["國"] == 80)
condition2 = (concat_df["數"] > 60)
condition3 = (concat_df["英"] > 70)
concat_df[(condition1 & condition2 & condition3)]

資料新增

新增column並加上資料,採用insert()方法
df.insert(位置索引值,column="欄位名稱",value="該筆資料的值")

新增一個叫物理的欄位名稱在索引值為1(第二個欄位)的位置,裡面的值是[80, 90, 100]

1
2
phy_arr=[80, 90, 100]
df.insert(1, column="物理", value=phy_arr)

空的資料填充

NaN的資料代換成自訂的資料,語法: fillna(要替換的值)
範例:

1
df.fillna(0)

資料刪除

DataFrame.drop(labels=None,axis=0, index="索引值", columns="欄位名", inplace=False)

參數說明:

  • labels: 要刪除的行/列的名字
  • axis: 預設為0,指刪除列(row);若要刪除行(column)時要指定axis=1;
  • index: 直接指定要刪除的列(row)
  • columns: 直接指定要刪除的行(column)
  • inplace =False,預設不改變原資料,而是回傳一個執行刪除操作後的新dataframe;
  • inplace=True,會在原數據上進行刪除操作,無返回值。

因此,刪除行列有兩種方式:
1)labels=None,axis=0的組合
2)index或columns直接指定要刪除的行或列

注意

  1. 指定參數axis = 0表示要刪除的值(row),axis = 1表示要刪除欄位(column)。
  2. 刪除資料的話,預設不改變原資料,而是回傳刪除後的新表格,所以要取新表格的資料要採用賦值的方式

刪除欄位列(column)

假設今天要刪除物理

1
2
3
4
5
# 刪除欄位
df.drop("物理", axis=1)

# 或是
df.drop(columns="物理")

刪除列(row)

刪除索引值(index)為student1的列

1
2
3
4
df.drop("student1")

#或是
df.drop(index=["student1"])

若要刪除多個值,給定一個list即可。

刪除多個列也同理。

刪除空值

有時候得到的資料不一定是完全都有數值,很可能含有NaN,這時候就需要把它給刪除。
df.dropna()

資料排序

sort_values()

指定欄位的數值排序採用.sort_values("欄位名", ascending=True, axis=0)方法,ascending=Trueaxis=0為預設的排列方式

1
2
3
4
df.sort_values("物理", ascending=True)

# 順序反轉
df.sort_values("物理", ascending=False)

axis=1時,改以行(columns)為排序方式

1
2
3
4
df.sort_values("student1", axis=1)

# 反轉
df.sort_values("student1", ascending=False, axis=1)

合併資料

合併多個CSV檔成單一DataFrame,若遇上相同類型的資料被分成多個不同的 CSV檔的情形,可以將之合併。

範例

假設本地分別有scores1.csvscores2.csv兩個檔案。

1
2
3
4
5
scores1_df = pd.read_csv("scores1.csv", encoding="utf-8-sig", index_col=0)
print(scores1_df)
# ========
scores2_df = pd.read_csv("scores2.csv", encoding="utf-8-sig", index_col=0)
print(scores2_df)

讀取DataFrames後發現格式一模一樣,可以將其進行合併。
使用pd.concat 將資料格式相同但分散在不同CSV檔合併成單一 DataFrame,方便之後處理。

1
2
concat_df = pd.concat([scores1_df, scores2_df],axis=0)
concat_df

改變欄位名稱

方法一: df.rename(rename_dic, axis=1)

透過df.rename(rename_dic, axis=1)方法,回傳一個新的df,不改變原始df

pandas預設處理的軸為列(row):以axis=0表示;而axis=1表示想以行(column)為單位

1
2
3
4
## 方法一: df.rename(rename_dic, axis=1),不改變原始df
rename_dic = {"age": "a", "city": "ct"}
new_df = df.rename(rename_dic, axis=1)
new_df

方法二: df.columns()

透過df.columns()方法,會改變原始df,對目標欄位重新命名。

1
2
3
## 方法二:  df.columns() 
df.columns = ['na', 'id'] + list(df.columns[2:])
df

參考資料

Python for Data Science
tutorials
[第 14 天] 常用屬性或方法(3)Data Frame

資料科學家的 pandas 實戰手冊:掌握 40 個實用數據技巧

[Day08]Pandas資料的取得與篩選!

Comments