Pandas 基于多标签(复合键)将长转宽
Pandas convert long to wide based on multi labels(composite keys)
我有一个看起来像这样的数据框
df_input = pd.DataFrame({'datatype':['IN','IN','EX','EX','IN','IN','EX','EX'], 'Time': [0,0,0,0,1,1,1,1], 'filetype': ['img','txt','img','txt','img','txt','img','txt']}, index=['PMSN01001','PMSN01001','PMSN01001','PMSN01001','PMSN01001','PMSN01001','PMSN01001','PMSN01001'])
print(df_input)
id datatype Time filetype
PMSN01001 IN 0 img
PMSN01001 IN 0 txt
PMSN01001 EX 0 img
PMSN01001 EX 0 txt
PMSN01001 IN 1 img
PMSN01001 IN 1 txt
PMSN01001 EX 1 img
PMSN01001 EX 1 txt
我想将数据框从长格式重塑为宽格式,如下所示。我在社区中看到过很多解决方案,但很少有处理列名称设置的直观且简单到足以让像我这样的初学者理解的。 我知道我必须以某种方式使用 .Pivot 但我正在努力解决两件事:设置列名的简单方法以及如何设置多索引(复合主键)
一文不值,对于每个id,加上['datatype'、'Time'、'filetype'],最多可以组成8条数据记录(2x2x2)。所以旋转列也应该相应地反映..我认为..
df_output = pd.DataFrame({'datatype_time0':['IN'], 'Time_time0': [0], 'filetype_time0': ['img'],'filetype2_time0':['txt'], 'datatype_time1':['EX'], 'Time_time1':[1], 'filetype_time1': ['img'],'filetype2_time1':['txt']}, index=['PMSN01001'])
df_output
datatype_time0 Time_time0 filetype_time0 filetype2_time0 datatype_time1 Time_time1 filetype_time1 filetype2_time1
PMSN01001 IN 0 img txt EX 1 img txt
我愿意接受任何重命名列名的方法,只要我能跟踪哪些值属于什么
谢谢
尝试使用 groupby
、cumcount
和 pivot_table
:
x = df.groupby(['id', 'datatype']).agg(Time=('Time', 'first'), filetype1=('filetype', 'first'), filetype2=('filetype', 'last'))
x = x.assign(idx=x.groupby(level=0).cumcount() + 1).reset_index().pivot_table(index=['id'], columns='idx',
values=['datatype', 'Time', 'filetype1', 'filetype2'], aggfunc='first')
x = x.sort_index(axis=1, level=1)
x = x.set_axis([f'{x}_{y}' for x,y in x.columns], axis=1).reset_index()
>>> x
id Time_1 datatype_1 filetype1_1 filetype2_1 Time_2 datatype_2 filetype1_2 filetype2_2
0 PMSN01001 1 EX img txt 0 IN img txt
>>>
我有一个看起来像这样的数据框
df_input = pd.DataFrame({'datatype':['IN','IN','EX','EX','IN','IN','EX','EX'], 'Time': [0,0,0,0,1,1,1,1], 'filetype': ['img','txt','img','txt','img','txt','img','txt']}, index=['PMSN01001','PMSN01001','PMSN01001','PMSN01001','PMSN01001','PMSN01001','PMSN01001','PMSN01001'])
print(df_input)
id datatype Time filetype
PMSN01001 IN 0 img
PMSN01001 IN 0 txt
PMSN01001 EX 0 img
PMSN01001 EX 0 txt
PMSN01001 IN 1 img
PMSN01001 IN 1 txt
PMSN01001 EX 1 img
PMSN01001 EX 1 txt
我想将数据框从长格式重塑为宽格式,如下所示。我在社区中看到过很多解决方案,但很少有处理列名称设置的直观且简单到足以让像我这样的初学者理解的。 我知道我必须以某种方式使用 .Pivot 但我正在努力解决两件事:设置列名的简单方法以及如何设置多索引(复合主键)
一文不值,对于每个id,加上['datatype'、'Time'、'filetype'],最多可以组成8条数据记录(2x2x2)。所以旋转列也应该相应地反映..我认为..
df_output = pd.DataFrame({'datatype_time0':['IN'], 'Time_time0': [0], 'filetype_time0': ['img'],'filetype2_time0':['txt'], 'datatype_time1':['EX'], 'Time_time1':[1], 'filetype_time1': ['img'],'filetype2_time1':['txt']}, index=['PMSN01001'])
df_output
datatype_time0 Time_time0 filetype_time0 filetype2_time0 datatype_time1 Time_time1 filetype_time1 filetype2_time1
PMSN01001 IN 0 img txt EX 1 img txt
我愿意接受任何重命名列名的方法,只要我能跟踪哪些值属于什么
谢谢
尝试使用 groupby
、cumcount
和 pivot_table
:
x = df.groupby(['id', 'datatype']).agg(Time=('Time', 'first'), filetype1=('filetype', 'first'), filetype2=('filetype', 'last'))
x = x.assign(idx=x.groupby(level=0).cumcount() + 1).reset_index().pivot_table(index=['id'], columns='idx',
values=['datatype', 'Time', 'filetype1', 'filetype2'], aggfunc='first')
x = x.sort_index(axis=1, level=1)
x = x.set_axis([f'{x}_{y}' for x,y in x.columns], axis=1).reset_index()
>>> x
id Time_1 datatype_1 filetype1_1 filetype2_1 Time_2 datatype_2 filetype1_2 filetype2_2
0 PMSN01001 1 EX img txt 0 IN img txt
>>>