在Pandas中编写自定义聚合函数
python中的Pandas广泛用于数据分析,它由一些精细的数据结构组成,如Dataframe和Series。在pandas中,有几个函数被证明对程序员有很大的帮助,其中之一就是聚合函数。这个函数从作为输入的多个值中返回一个单一的值,这些值根据某些标准被分组。一些聚合函数包括平均数、计数、最大值,以及其他函数。
语法:
DataFrame.agg(func=None, axis=0, *args, **kwargs)
参数:
- axis: {0或’index’, 1或’columns’} = 0或’index’意味着函数被应用于每一列,1或’columns’意味着函数被应用于每一行。
- func: function, str, list or dict = 它描述了要用于聚合的函数。接受的组合是:函数、字符串函数名(str)、函数列表(list/dict)。
- *args:它指定了要传递给函数的位置参数。
- **kwargs:它指定了要传递给函数的关键字参数。
返回:该函数可以返回标量、系列或Dataframe。当Series.agg被单个函数调用时,返回标量;当Dataframe.agg被单个函数调用时,返回Series;当Dataframe.agg被多个函数调用时,返回Dataframe。
让我们创建一个Dataframe。
# import pandas library
import pandas as pd
# create a Dataframe
df = pd.DataFrame([[10, 20, 30],
[40, 50, 60],
[70, 80, 90],
[100,110,120]],
columns=['Col_A', 'Col_B',
'Col_C'])
# show the dataframe
df
输出:
现在,让我们执行一些操作。
1.对行进行聚合:这是对数据框架的行执行聚合函数。正如你在下面的例子中看到的,例子1在聚合函数里面有两个关键词,sum和min。sum将每行的第一个(10,40,70,100)、第二个(20,50,80,110)和第三个(30,60,90,120)元素分别相加并打印出来,min在各行的元素中找到最小的数字并打印出来。第二个例子也是类似的过程。
示例 1:
df.agg(['sum', 'min'])
输出:
示例 2:
df.agg(['sum', 'min', 'max'])
输出:
2.Performing aggregation per column:这是在列上执行聚合功能,列被特别选择,如例子中所示。在第一个例子中,选择了两列,’Col_A’和’Col_B’,要对它们进行操作。对于Col_A,计算最小值和总和值,对于Col_B,计算最小值和最大值。例2也是类似的过程。
示例 1:
df.agg({'Col_A' : ['sum', 'min'],
'Col_B' : ['min', 'max']})
输出:
示例 2:
df.agg({'Col_A' : ['sum', 'min'],
'Col_B' : ['min', 'max'],
'Col_C' : ['sum', 'mean']})
输出:
注意:如果没有对某一列进行特定的聚合,它将打印NaN。
3.在列上执行聚合:这是在列上执行聚合功能。如例1所示,每一列的第一(10,20,30)、第二(40,50,60)、第三(70,80,90)和第四(100,110,120)元素的平均值被分别计算并打印。
示例:
df.agg("mean", axis = "columns")
输出:
4 .自定义聚合函数:有时需要创建我们自己的聚合函数。
例子:考虑一个由学生身份(stu_id)、科目代码(sub_code)和分数(mark)组成的数据框。
# import pandas library
import pandas as pd
# Creating DataFrame
df = pd.DataFrame(
{'stud_id' : [101, 102, 103, 104,
101, 102, 103, 104],
'sub_code' : ['CSE6001', 'CSE6001', 'CSE6001',
'CSE6001', 'CSE6002', 'CSE6002',
'CSE6002', 'CSE6002'],
'marks' : [77, 86, 55, 90,
65, 90, 80, 67]}
)
# Printing DataFrame
df
输出:
现在,如果你需要计算每个学生(唯一的stu_id)的总分数(两个科目的分数)。这个过程可以使用自定义聚合函数来完成。这里我的自定义聚合函数是’total’。
# Importing reduce for
# rolling computations
from functools import reduce
# define a Custom aggregation
# function for finding total
def total(series):
return reduce(lambda x, y: x + y, series)
# Grouping the output according to
# student id and printing the corresponding
# total marks and to check whether the
# output is correct or not, sum function
# is also used to print the sum.
df.groupby('stud_id').agg({'marks': ['sum', total]})
输出:
正如你所看到的,两列的总分值相同,所以我们的聚合函数在这种情况下正确计算了总分。