我有一个数据库中的数据样本,我想在python中将其从垂直调整为水平,以进行进一步的数据分析。 数据框如下所示:
ID measured_at weight
aa 2017-11-04 78.1
bb 2018-04-08 74.2
bb 2018-04-16 73.2
bb 2018-04-28 72.1
cc 2018-03-02 90.2
cc 2018-03-20 88.9
我希望它看起来像这样:
id date1 weight1 date2 weight2 date3 weight3
aa 2017-11-04 78.1 NA NA NA NA
bb 2018-04-08 74.2 2018-04-16 73.2 2018-04-28 72.1
cc 2018-03-02 90.2 2018-03-20 88.9 NA NA
某些ID的测量值超过3,因此需要为同一ID上的每个新测量值生成新的日期和权重列。
这怎么办?
答案 0 :(得分:0)
您可以将GroupBy
与list
一起使用两次,然后再使用pd.concat
。
我将重命名列和将索引提升到列作为练习。
g = df.groupby('ID')
df_dates = pd.DataFrame(g['measured_at'].apply(list).values.tolist(), index=g.groups)
df_weights = pd.DataFrame(g['weight'].apply(list).values.tolist(), index=g.groups)
df_dates.columns = df_dates.columns * 2
df_weights.columns = df_weights.columns * 2 + 1
res = pd.concat([df_dates, df_weights], axis=1).sort_index(1)
print(res)
0 1 2 3 4 5
aa 2017-11-04 78.1 None NaN None NaN
bb 2018-04-08 74.2 2018-04-16 73.2 2018-04-28 72.1
cc 2018-03-02 90.2 2018-03-20 88.9 None NaN
答案 1 :(得分:0)
IIUC使用cumcount
创建帮助键。
df['helpkey']=df.groupby('ID').cumcount()+1
newdf=df.set_index(['ID','helpkey']).unstack().sort_index(level=1,axis=1)
newdf.columns=newdf.columns.map('{0[0]}_{0[1]}'.format)
newdf
Out[608]:
measured_at_1 weight_1 measured_at_2 weight_2 measured_at_3 weight_3
ID
aa 2017-11-04 78.1 None NaN None NaN
bb 2018-04-08 74.2 2018-04-16 73.2 2018-04-28 72.1
cc 2018-03-02 90.2 2018-03-20 88.9 None NaN
答案 2 :(得分:0)
将groupby
与nth
一起使用:
d2 = df.groupby('ID')
new_df = pd.DataFrame()
for i in range(len(d2)):
new_df = pd.concat([new_df, d2.nth(i).add_suffix(i+1)], axis=1)
给出
measured_at1 weight1 measured_at2 weight2 measured_at3 weight3
aa 2017-11-04 78.1 NaN NaN NaN NaN
bb 2018-04-08 74.2 2018-04-16 73.2 2018-04-28 72.1
cc 2018-03-02 90.2 2018-03-20 88.9 NaN NaN