pandas所有的高阶分组统计用法都在这里(建议收藏哦)

本篇文章着重介绍一下分组统计的进阶用法:

pandas所有的高阶分组统计用法都在这里(建议收藏哦)

第一部分:分组:

根据现有的列去分组

这也是最简单的,可以根据一个键,也可以传入列表支持多个键:

创建数据:

df = pd.DataFrame({'A': ['a', 'b', 'a', 'c', 'a', 'c', 'b', 'c'],
'B': [2, 8, 1, 4, 3, 2, 5, 9],
'C': [102, 98, 107, 104, 115, 87, 92, 123]})
df
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

根据一个键:

df.groupby("A").sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

根据两个键:

df.groupby(["A","B"]).sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

根据字典映射去分组:

mapping={"A":1,"B":1,"C":2}
df.groupby(mapping,axis=1).sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

mapping={0:1,1:1,2:2,3:2,4:1,5:1,6:1,7:1}
df.groupby(mapping).sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

应为A列是文本,pandas自动剔除了

根据列表(字典的简便写法):

但是有一个前提:必须是提供行或者列相等长度的列表:

mapping=[1,1,4]
df.groupby(mapping,axis=1).sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

字典可以不相等吗?,可以,但是没有映射的数据将不在统计范围内:

mapping={0:1,1:1,2:2}
df.groupby(mapping).sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

mapping={"A":1,"B":1}
df.groupby(mapping,axis=1).sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

扩展:因为字典的映射关系,我们也可以用映射去筛选需要统计的数据去透视

根据自定义区间分组:

这里用到了cut函数,后面我会详细介绍这个函数

dd_2=pd.cut(df['B'], bins=2)
df.groupby(dd_2).sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

如果我们有一些数据,这些数据是包含年龄的,就可以根据这个方法来区分不同年龄段,也可以区分不同的时间段,反正用着的时候挺好用的

根据函数去分组:

根据函数分组的原理就是根据返回值来分组,相同的返回值将会被分为一组:

默认传给函数的是索引:

def f(x):
print(x)
return x
df.groupby(f).sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

def f(x):
print(x)
return x>5
df.groupby(f).sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

如果想用别的列应用函数:

def f(x):
print(x)
return pd.cut(x,bins=3)
df.groupby(f(df["C"])).sum()
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

第二部分:统计计算

pandas在分组后的统计计算中,有一些常用的经过优化的一些方法:

pandas所有的高阶分组统计用法都在这里(建议收藏哦)

今天要讲的是如何应用这些方法

第一个介绍的是agg(Aggregate):

Aggregate using one or more operations over the specified axis

使用指定轴上的一个或多个操作进行聚合

意思是说,在指定的轴上使用一个或多个聚合函数

df.groupby("A").agg({"B":np.sum,"C":np.mean})
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

df.groupby("A").agg({"B":[np.sum,np.mean],"C":np.mean})
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

df.groupby('A')['B'].agg({'mean':np.mean, 'standard deviation': np.std})
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

第二个介绍:apply最重要的一个函数

df.groupby('A').apply(lambda x: x['C']-x['B'])
df.groupby('A').apply(lambda x: (x['C']-x['B']).mean())
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

想要用好apply还要明白他的原理:

首先来看看是如何分组的,这次利用groupby的迭代器读取分组的数据:

for a,b in df.groupby('A'):
print(a)
print(b)
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

自定义函数应用时传入的就是每一个分组数据,你可以利用DataFrame的特性来筛选相应的列然后用来计算,具体能达到什么效果完全看你的想法了

注意:当你在根据键分组后具体返回什么也是靠你的自定义函数.

比如,我们分组后只返回B列的数据:

def f(x):
return x["B"]
df.groupby("A").apply(f)

返回B的平方:

def f(x):
return x["B"]**2
df.groupby("A").apply(f)
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

apply能达到的不仅仅这一点:

下面我们计算一下每个分组的B列最大值和最小值的差:

def f(x):
return max(x["B"])-min(x["B"])
df.groupby("A").apply(f)
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

下面我们统计每个分组的最后一行数据,这个要求在很多工具里面是很难实现的

def f(x):
return x[-1:]
df.groupby("A").apply(f)
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

想要用好apply的核心就在于:分组后传入apply自定义函数的就是每个分组的DataFrame,返回值就是按照你的自定义函数来的。

最后介绍的一个函数是transform()

前面进行聚合运算的时候,得到的结果是一个以分组名为 index 的结果对象。如果我们想使用原数组的 index 的话,就需要进行 merge 转换。transform(func, args, *kwargs) 方法简化了这个过程,它会把 func 参数应用到所有分组,然后把结果放置到原数组的 index 上(如果结果是一个标量,就进行广播):

df.groupby("A")["B"].transform(np.sum)
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

自定义函数:

def f(x):
return max(x)-min(x)
df.groupby("A")["B"].transform(f)
pandas所有的高阶分组统计用法都在这里(建议收藏哦)

总结:

agg:适用于常用的函数算法

apply:适合自定义,功能强大,需要编写函数,注意返回值

transform:如果你不想改变原有index,就需要用它


分享到:


相關文章: