我刚刚开始学习熊猫,并想知道它们pandas groupby
和pandas pivot_table
功能之间是否有任何区别.任何人都可以帮我理解它们之间的区别.帮助将不胜感激.
Dav*_*ust 61
双方pivot_table
并groupby
用于收集您的数据帧.差异仅在于结果的形状.
使用pd.pivot_table(df, index=["a"], columns=["b"], values=["c"], aggfunc=np.sum)
表创建a
在行轴上,b
在列轴上,并且值是总和c
.
例:
df = pd.DataFrame({"a": [1,2,3,1,2,3], "b":[1,1,1,2,2,2], "c":np.random.rand(6)})
pd.pivot_table(df, index=["a"], columns=["b"], values=["c"], aggfunc=np.sum)
b 1 2
a
1 0.528470 0.484766
2 0.187277 0.144326
3 0.866832 0.650100
Run Code Online (Sandbox Code Playgroud)
使用时groupby
,给定的尺寸放在列中,并为这些尺寸的每个组合创建行.
在这个例子中,我们创建了一系列的值的总和c
,由所有唯一组合进行分组a
和b
.
df.groupby(['a','b'])['c'].sum()
a b
1 1 0.528470
2 0.484766
2 1 0.187277
2 0.144326
3 1 0.866832
2 0.650100
Name: c, dtype: float64
Run Code Online (Sandbox Code Playgroud)
类似的用法groupby
是,如果我们省略['c']
.在这种情况下,它会创建一个数据帧(而不是一系列),其中所有剩余列的总和按唯一值和a
和分组b
.
print df.groupby(["a","b"]).sum()
c
a b
1 1 0.528470
2 0.484766
2 1 0.187277
2 0.144326
3 1 0.866832
2 0.650100
Run Code Online (Sandbox Code Playgroud)
cot*_*ail 21
groupby
和pivot_table
的关系如下(事实上,在底层pivot_table
是使用 定义的groupby
)1:
特别是,如果不使用columns
参数,则和两者都会产生相同的结果(如果使用相同的聚合器函数)。pivot_table()
groupby()
pivot_table()
# sample
df = pd.DataFrame({"a": [1,1,1,2,2,2], "b": [1,1,2,2,3,3], "c": [0,0.5,1,1,2,2]})
# example
gb = df.groupby(['a','b'])[['c']].sum()
pt = df.pivot_table(index=['a','b'], values=['c'], aggfunc='sum')
# equality test
gb.equals(pt) # True <--- no `columns=` kwarg, no `unstack()`
Run Code Online (Sandbox Code Playgroud)
如果您熟悉 Microsoft Excel,则pivot_table
和 的groupby
行为类似于 Excel 中的数据透视表功能:
groupby
:by
kwarg(即石斑鱼列)对应于 ROWS,聚合的列对应于 VALUES,groupby 方法(mean()
等sum()
)对应于您在值字段设置中选择的函数。pivot_table
:values
kwarg 对应于 VALUES、index
对应于 ROWS、columns
对应于 COLUMNS 以及aggfunc
对应于您在值字段设置中选择的函数。在 pandas 中,就像在 Excel 中一样,groupby
会产生长堆叠表,而pivot_table
会产生宽表。如果从 中取消长表的堆叠groupby
,您会得到与 相同的结果pivot_table
。
1一般来说,如果我们查看源代码,pivot_table()
内部会调用__internal_pivot_table()
. 此函数从索引和列中创建一个单一的平面列表,并groupby()
使用该列表作为石斑鱼进行调用。然后在聚合之后,调用unstack()
列列表。
如果列从未被传递,则没有任何内容可以取消堆叠,因此groupby
会pivot_table
产生相同的输出。
这种连接的演示是:
gb = (
df
.groupby(['a','b'])[['c']].sum()
.unstack(['b'])
)
pt = df.pivot_table(index=['a'], columns=['b'], values=['c'], aggfunc='sum')
gb.equals(pt) # True <--- they produce the same output
Run Code Online (Sandbox Code Playgroud)
正如stack()
的逆运算一样unstack()
,以下也成立:
pt = df.pivot_table(index=['a'], columns=['b'], values=['c'], aggfunc='sum').stack(['b'])
gb = df.groupby(['a','b'])[['c']].sum()
pt.equals(gb) # True <--- they produce the same output
Run Code Online (Sandbox Code Playgroud)
总之,根据用例,一种比另一种更方便,但它们都可以代替另一种使用,并且在正确应用stack()
/后unstack()
,两者将产生相同的输出。
但是,这两种方法之间存在性能差异。简而言之,pivot_table()
比 慢groupby().agg().unstack()
。您可以从此答案中了解更多相关信息。
小智 11
它更适合使用.pivot_table()
,而不是.groupby()
当你需要表现出与行和列标签聚集。
.pivot_table()
使同时创建行和列标签变得容易并且更可取,即使您可以通过.groupby()
很少的额外步骤获得类似的结果。