[英]pandas dataframe wide to long
我有一個 dataframe 像這樣:
id type count_x count_y count_z sum_x sum_y sum_z
1 A 12 1 6 34 43 25
1 B 4 5 8 12 37 28
現在我想通過按id
和type
分組來轉換它,然后像這樣從寬轉換為長:
id type variable value calc
1 A x 12 count
1 A y 1 count
1 A z 6 count
1 B x 4 count
1 B y 5 count
1 B z 8 count
1 A x 34 sum
1 A y 43 sum
1 A z 25 sum
1 B x 12 sum
1 B y 37 sum
1 B z 28 sum
我怎樣才能做到這一點?
嘗試使用melt
:
res = pd.melt(df,id_vars=['id', 'type'])
res[['calc', 'variable']] = res.variable.str.split('_', expand=True)
ID | 類型 | 多變的 | 價值 | 計算 | |
---|---|---|---|---|---|
0 | 1 | 一個 | X | 12 | 數數 |
1 | 1 | 乙 | X | 4 | 數數 |
2 | 1 | 一個 | 是的 | 1 | 數數 |
3 | 1 | 乙 | 是的 | 5 | 數數 |
4 | 1 | 一個 | z | 6 | 數數 |
5 | 1 | 乙 | z | 8 | 數數 |
6 | 1 | 一個 | X | 34 | 和 |
7 | 1 | 乙 | X | 12 | 和 |
8 | 1 | 一個 | 是的 | 43 | 和 |
9 | 1 | 乙 | 是的 | 37 | 和 |
10 | 1 | 一個 | z | 25 | 和 |
11 | 1 | 乙 | z | 28 | 和 |
使用stack
:
df1 = (df.set_index(['id', 'type']).stack().rename('value').reset_index())
df1 = df1.drop('level_2',axis=1).join(df1['level_2'].str.split('_', 1, expand=True).rename(columns={0:'calc', 1:'variable'}))
ID | 類型 | 價值 | 計算 | 多變的 | |
---|---|---|---|---|---|
0 | 1 | 一個 | 12 | 數數 | X |
1 | 1 | 一個 | 1 | 數數 | 是的 |
2 | 1 | 一個 | 6 | 數數 | z |
3 | 1 | 一個 | 34 | 和 | X |
4 | 1 | 一個 | 43 | 和 | 是的 |
5 | 1 | 一個 | 25 | 和 | z |
6 | 1 | 乙 | 4 | 數數 | X |
7 | 1 | 乙 | 5 | 數數 | 是的 |
8 | 1 | 乙 | 8 | 數數 | z |
9 | 1 | 乙 | 12 | 和 | X |
10 | 1 | 乙 | 37 | 和 | 是的 |
11 | 1 | 乙 | 28 | 和 | z |
您可以結合使用 melt 和 split()
df = pd.DataFrame({'id': [1,1], 'type': ['A', 'B'], 'count_x':[12,4], 'count_y': [1,5], 'count_z': [6,8], 'sum_x': [34, 12], 'sum_y': [43, 37], 'sum_z': [25, 28]})
df_melt = df.melt(id_vars=['id', 'type'])
df_melt[['calc', 'variable']] = df_melt['variable'].str.split("_", expand=True)
df_melt
id type variable value calc
0 1 A x 12 count
1 1 B x 4 count
2 1 A y 1 count
3 1 B y 5 count
4 1 A z 6 count
5 1 B z 8 count
6 1 A x 34 sum
7 1 B x 12 sum
8 1 A y 43 sum
9 1 B y 37 sum
10 1 A z 25 sum
11 1 B z 28 sum
假設您的 pandas DataFrame 是df_wide
,您可以在df_long
中獲得所需的結果,
df_long = df.melt(id_vars=['id', 'type'], value_vars=['count_x', 'count_y', 'count_z', 'sum_x', 'sum_y', 'sum_z'])
df_long['calc'] = df_long['variable'].apply(lambda x: x.split('_')[0])
df_long['variable'] = df_long['variable'].apply(lambda x: x.split('_')[1])
您可以使用pyjanitor中的pivot_longer重塑數據:
df.pivot_longer(index = ['id', 'type'],
# names of the new columns
# note the order
names_to = ['calc', 'variable'],
values_to = 'value',
# delimiter for the columns
# first value is assigned to `calc`,
# the other goes to `variable`
names_sep='_')
id type calc variable value
0 1 A count x 12
1 1 B count x 4
2 1 A count y 1
3 1 B count y 5
4 1 A count z 6
5 1 B count z 8
6 1 A sum x 34
7 1 B sum x 12
8 1 A sum y 43
9 1 B sum y 37
10 1 A sum z 25
11 1 B sum z 28
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.