use*_*ser 5 python matrix dataframe pandas
我有一个数据框 df,例如:
A = [["John", "Sunday", 6], ["John", "Monday", 3], ["John", "Tuesday", 2], ["Mary", "Sunday", 6], ["Mary", "Monday", 4], ["Mary", "Tuesday", 7]]
df = pandas.DataFrame(A, columns=["names", "dates", "times"])
Run Code Online (Sandbox Code Playgroud)
我想重塑它,这样,而不是三列,我可以创建一个矩阵,其中第一列索引行,第二列索引列,第三列成为矩阵值,例如:
B = [["John", 6, 3, 2], ["Mary", 6, 4, 7]]
df2 = pandas.DataFrame(B, columns=["names", "Sunday", "Monday", "Tuesday"])
Run Code Online (Sandbox Code Playgroud)
甚至更好:
B = numpy.asarray(B)
B = pandas.DataFrame(B)
Run Code Online (Sandbox Code Playgroud)
怎么把A变成B?
我创建了一个双 for 循环,但在我的情况下 df 非常大并且需要很长时间。有没有更好的方法来做到这一点?
这不仅仅是重塑,因为 A 有 18 个值,B 有 8 个
您可以使用pivot_table(),例如:
In []:
df.pivot_table(columns='dates', index='names', values='times').reset_index()
Out[]:
dates names Monday Sunday Tuesday
0 John 3 6 2
1 Mary 4 6 7
Run Code Online (Sandbox Code Playgroud)
尝试:
df.set_index(['names','dates'])['times'].unstack().reset_index()
Run Code Online (Sandbox Code Playgroud)
输出:
dates names Monday Sunday Tuesday
0 John 3 6 2
1 Mary 4 6 7
Run Code Online (Sandbox Code Playgroud)
或者:
pd.crosstab(df.names, df.dates, df.times, aggfunc='sum').reset_index()
Run Code Online (Sandbox Code Playgroud)
或者:
df.groupby(['names','dates']).sum()['times'].unstack().reset_index()
Run Code Online (Sandbox Code Playgroud)
或者:
df.pivot('names','dates','times').reset_index()
Run Code Online (Sandbox Code Playgroud)