Pandas使用unstack()行转列时报错:Index contains duplicate entries, cannot reshape

unstack实例:DataFrame 去除一对多关系之行转列方法详解(附unstack()使用场景及代码)

stack()即“堆叠”,作用是将列旋转到行
unstack()即stack()的反操作,将行旋转到列

unstack(): Series对象的API,用于将Series的数据类型转DataFrame类型(因为DataFrame提供的数据操作API远远多于Series)。(Series视作一维,DataFrame视作高维数据,类比一维数组和高维度数组)

报错原因:用unstack操作的数据必须唯一标识
首先看可以行转列的数据形式:

转换前
Pandas使用unstack()行转列时报错:Index contains duplicate entries, cannot reshape_第1张图片

代码:

# 将"姓名"和"科目"设置为索引, 然后取出"分数"这一列, 得到的对应的具有二级索引的Series对象
two_level_index_series = df.set_index(["姓名", "科目"])["分数"]
# 调用具有二级索引的Series的unstack, 会得到一个DataFrame
# 并会自动把一级索引变成DataFrame的索引, 二级索引变成DataFrame的列
new_df = two_level_index_series.unstack()
print(new_df)
"""
科目    数学  英语   语文
姓名               
古明地觉  95  96   90
琪露诺    9  91  100
芙兰朵露  92  98   87
"""

# 是不是改回来了呢? 但是还有不完美的地方, 这个DataFrame的索引和列都有一个名字
# 索引的名字叫"姓名", 列的名字叫"科目", 因为原来Series的两个索引就叫"姓名"和"科目"
# 可以通过 rename_axis(index=, columns=) 来给坐标轴重命名
new_df = new_df.rename_axis(columns=None)

# 这里我们只给列重命名, 没有给索引重命名, 至于原因请往下看
new_df = new_df.reset_index()
print(new_df)
"""
     姓名  数学  英语   语文
0  古明地觉  95  96   90
1   琪露诺   9   91  100
2  芙兰朵露  92  98   87
"""
# 大功告成, 如果index的名字变为空的话, 那么reset_index之后, 列名就会变成index
# 但如果原来的索引有名字, 那么reset_index之后, 列名就是原来的索引名

转换过后:Pandas使用unstack()行转列时报错:Index contains duplicate entries, cannot reshape_第2张图片

推荐阅读原博客:pandas行转列、列转行、以及一行生成多行

错误数据形式:
Pandas使用unstack()行转列时报错:Index contains duplicate entries, cannot reshape_第3张图片
试图行转列的报错代码:

model_unstack_df=model1_df.set_index(['report_id','position'])['name'].unstack().add_prefix('position_').add_suffix('_name')
model_unstack_df.head()

分析:

这里的report_id=548947422542434000【红框】时,position对应有三个不同的name,索引包含重复的条目,unstack()就无法重新设置其形状;

而report_id=548947422542434001【篮框】时,position和name是一一对应的,可以行转列。

你可能感兴趣的:(遇到的一些问题,unstack,pandas,python,行转列)