本文旨在介绍如何使用 Pandas DataFrame 对数据进行分组聚合,并计算特定列的百分比。我们将通过一个实际案例,演示如何按设备 (Device) 对带宽使用情况 (Bw_in, Bw_out) 进行汇总,并计算其占总流量 (In, Out) 的百分比,从而高效地实现数据分析目标。
使用 groupby() 和 transform() 进行数据聚合
在 Pandas 中,groupby() 函数允许你根据一个或多个列的值将 DataFrame 分组。然后,你可以对每个组应用聚合函数,例如 sum()、mean()、count() 等。 transform() 函数则允许我们将聚合后的值广播回原始 DataFrame,这对于计算百分比等需要比较每个组内值与组总和的情况非常有用。
示例:
假设我们有以下 DataFrame:
import pandas as pd data = {'Device': ['Usa123', 'Usa123', 'Emea01', 'Emea01'], 'int': ['Eth1', 'Eth0', 'Wan1', 'Eth3'], 'In': [1000, 10000, 1000, 2000], 'Out': [500, 700, 500, 1000], 'Bw_in': [100, 200, 150, 200], 'Bw_out': [75, 80, 90, 70]} df = pd.DataFrame(data) print(df)
输出:
Device int In Out Bw_in Bw_out 0 Usa123 Eth1 1000 500 100 75 1 Usa123 Eth0 10000 700 200 80 2 Emea01 Wan1 1000 500 150 90 3 Emea01 Eth3 2000 1000 200 70
现在,我们要计算每个设备的 %InUsage 和 %OutUsage,计算公式如下:
- %InUsage = Bw_in 总和 / In 总和 (按设备分组)
- %OutUsage = Bw_out 总和 / Out 总和 (按设备分组)
我们可以使用以下代码实现:
g = df.groupby("Device") df[["%InUsage", "%OutUsage"]] = ( g[["Bw_in", "Bw_out"]].transform("sum") / g[["In", "Out"]].transform("sum").to_numpy() ) print(df)
代码解释:
- g = df.groupby(“Device”): 这行代码根据 ‘Device’ 列对 DataFrame 进行分组,并将分组后的对象存储在变量 g 中。
- g[[“Bw_in”, “Bw_out”]].transform(“sum”): 这行代码对每个设备组的 ‘Bw_in’ 和 ‘Bw_out’ 列求和。transform(“sum”) 函数将计算得到的每个组的总和广播回原始 DataFrame,保持与原始 DataFrame 相同的索引。
- g[[“In”, “Out”]].transform(“sum”).to_numpy(): 这行代码对每个设备组的 ‘In’ 和 ‘Out’ 列求和,然后使用 .to_numpy() 将结果转换为 NumPy 数组。 这是因为 Pandas Series 和 DataFrame 在进行除法运算时,会进行索引对齐。为了避免索引对齐带来的潜在问题,我们将除数转换为 NumPy 数组。
- df[[“%InUsage”, “%OutUsage”]] = …: 这行代码将计算得到的 %InUsage 和 %OutUsage 添加到原始 DataFrame 中。
输出结果:
Device int In Out Bw_in Bw_out %InUsage %OutUsage 0 Usa123 Eth1 1000 500 100 75 0.027273 0.129167 1 Usa123 Eth0 10000 700 200 80 0.027273 0.129167 2 Emea01 Wan1 1000 500 150 90 0.116667 0.106667 3 Emea01 Eth3 2000 1000 200 70 0.116667 0.106667
注意事项
- 确保用于分组的列(例如,这里的 ‘Device’)包含正确的数据类型。
- 在进行除法运算时,要处理除数为零的情况,避免出现 ZeroDivisionError。 可以使用 fillna(0) 将 NaN 值替换为 0。
- 理解 transform() 函数的作用,它将聚合结果广播回原始 DataFrame,这使得我们可以方便地进行后续计算。
- 使用 .to_numpy() 将 Pandas Series 转换为 NumPy 数组,避免索引对齐问题,提高代码的健壮性。
总结
本文介绍了如何使用 Pandas 的 groupby() 和 transform() 函数对 DataFrame 进行分组聚合,并计算特定列的百分比。通过示例代码和详细解释,展示了如何高效地处理数据,并获得所需的结果。 这种方法避免了使用 apply 函数,从而提高了代码的执行效率。 掌握这些技巧可以帮助你更好地进行数据分析和处理。