公衆號:尤而小屋
作者:Peter
編輯:Peter
大家好,我是Peter~
本文介紹的是Pandas中4個行列轉換的方法,包含:
- melt
- 轉置T或者transpose
- wide_to_long
- explode(爆炸函數)
最後回答一個讀者朋友問到的數據處理問題。
Pandas行列轉換
pandas中有多種方法能夠實現行列轉換:
導入庫
import pandas as pd
import numpy as np
函數melt
melt的主要參數:
pandas.melt(frame,
id_vars=None,
value_vars=None,
var_name=None,
value_name='value',
ignore_index=True,
col_level=None)
下面解釋參數的含義:
frame:要處理的數據框DataFrame。
id_vars:表示不需要被轉換的列名
value_vars:表示需要轉換的列名,如果剩下的列全部都需要進行轉換,則不必寫
var_name和value_name:自定義設置對應的列名,相當於是取新的列名
igonore_index:是否忽略原列名,默認是True,就是忽略了原索引名,重新生成0,1,2,3,4....的自然索引
col_level:如果列是多層索引列MultiIndex,則使用此參數;這個參數少用
模擬數據
# 待轉換的數據:frame
df = pd.DataFrame({"col1":[1,1,1,1,1],
"col2":[3,3,3,3,3],
"col3":["a","a","a","b","b"]
})
df
id_vars
value_vars
上面兩個參數的同時使用:
同時轉換多個列屬性:
var_name和value_name
pd.melt(
df,
id_vars=["col1"], # 不變
value_vars=["col3"], # 轉變
var_name="col4", # 新的列名
value_name="col5" # 對應值的新列名
)
ignore_index
默認情況下是生成自然索引:
可以改成False,使用原來的索引:
轉置函數
pandas中的T屬性或者transpose函數就是實現行轉列的功能,準確地說就是轉置
簡單轉置
模擬了一份數據,查看轉置的結果:
使用transpose函數進行轉置:
還有另一個方法:先對值values進行轉置,再把索引和列名進行交換:
最後看一個簡單的案例:
wide_to_long函數
字面意思就是:將數據集從寬格式轉換爲長格式
wide_to_long(
df,
stubnames,
i,
j,
sep: str = "",
suffix: str = "\\d+"
參數的具體解釋:
- df:待轉換的數據框
- stubnames:寬表中列名相同的存部分
- i:要用作 id 變量的列
- j:給長格式的“後綴”列設置 columns
- sep:設置要刪除的分隔符。例如 columns 爲 A-2020,則指定 sep='-' 來刪除分隔符。默認爲空。
- suffix:通過設置正則表達式取得“後綴”。默認'\d+'表示取得數字後綴。沒有數字的“後綴”可以用'\D+'來取得
模擬數據
轉換過程
使用函數實施轉換:
設置多層索引
先模擬一份數據:
如果不習慣多層索引,可以轉成下面的格式:
sep和suffix
df5 = pd.DataFrame({
'a': [1, 1, 2, 2, 3, 3, 3],
'b': [1, 2, 2, 3, 1, 2, 3],
'stu_one': [2.8, 2.9, 1.8, 1.9, 2.2, 2.3, 2.1],
'stu_two': [3.4, 3.8, 2.8, 2.4, 3.3, 3.4, 2.9]
})
df5
pd.wide_to_long(
df5,
stubnames='stu',
i=['a', 'b'],
j='number',
sep='_', # 列名中存在連接符時使用;默認爲空
suffix=r'\w+') # 基於正則表達式的後綴;默認是數字\d+;這裏改成\w+,表示字母
爆炸函數-explode
explode(column, ignore_index=False)
這個函數的參數就只有兩個:
- column:待爆炸的元素
- ignore_index:是否忽略索引;默認是False,保持原來的索引
模擬數據
單個字段爆炸
對單個字段實施爆炸過程,將寬錶轉成長表:
參數ignore_index
多個字段爆炸
連續對多個字段實施爆炸的過程:
讀者解疑
在這裏回答一個讀者的問題,數據採用模擬的形式。有下面的這樣一份數據,需求:
每個shop下每個fruit在各自shop的佔比
fruit = pd.DataFrame({
"shop":["shop1","shop3","shop2","shop3",
"shop2","shop1","shop3","shop2",
"shop3","shop2","shop3","shop2","shop1"],
"fruit":["蘋果","葡萄","香蕉","蘋果",
"葡萄","橘子","梨","哈密瓜",
"葡萄","香蕉","蘋果","葡萄","橘子"],
"number":[100,200,340,150,
200,300,90,80,340,
150,200,300,90]})
fruit
首先我們是需要統計每個shop每個fruit的銷量
方法1:多步驟
方法1採用的是多步驟解決:
1、每個shop的總銷量
2、增加總和shop_sum列
3、生成佔比