pandas数据分组groupby()和统计函数agg()

举报
nineteens 发表于 2021/03/03 16:31:56 2021/03/03
【摘要】 pandas数据分组groupby和统计函数agg

  数据分组

  使用 groupby() 方法进行分组

  group.size()查看分组后每组的数量

  group.groups 查看分组情况

  group.get_group('名字') 根据分组后的名字选择分组数据

  准备数据

  # 一个Series其实就是一条数据,Series方法的第一个参数是data,第二个参数是index(索引),如果没有传值会使用默认值(0-N)

  # index参数是我们自定义的索引值,注意:参数值的个数一定要相同。

  # 在创建Series时数据并不一定要是列表,也可以将一个字典传进去。

  from pandas import Series, DataFrame

  # 使用字典创建

  index_list = ['001', '002', '003', '004', '005', '006', '007', '008', '009', '010']

  name_list = ['李白', '王昭君', '诸葛亮', '狄仁杰', '孙尚香', '妲己', '周瑜', '张飞', '王昭君', '大乔']

  age_list = [25, 28, 27, 25, 30, 29, 25, 32, 28, 26]

  gender_list = ['F', 'M', 'F', 'F', 'M', 'M', 'F', 'F', 'M', 'M']

  salary_list = ['10k', '12.5k', '20k', '14k', '12k', '17k', '18k', '21k', '22k', '21.5k']

  marital_list = ['NO', 'NO', 'YES', 'YES', 'NO', 'NO', 'NO', 'YES', 'NO', 'YES']

  dic = {

  '姓名': Series(data=name_list, index=index_list),

  '年龄': Series(data=age_list, index=index_list),

  '薪资': Series(data=salary_list, index=index_list),

  '性别': Series(data=gender_list, index=index_list),

  '婚姻状况': Series(data=marital_list, index=index_list)

  }

  df = DataFrame(dic)

  # 写入csv,path_or_buf为写入文本文件

  df.to_csv(path_or_buf='./People.csv', encoding='utf_8_sig')

  print('end')

  上面代码会在当前目录下生成一个 People.csv 文件

  import pandas as pd

  df = pd.read_csv('./People.csv')

  df.head()

  # 根据 '性别列' 进行分组, 得到的是一个分组后的对象

  groups = df.groupby('性别')

  print(groups)

  size()

  使用groupby的size方法可以查看分组后每组的数量, 并返回一个含有分组大小的Series

  print(groups.size())

  性别

  F 5

  M 5

  dtype: int64

  可以只对一列数据进行分组, 只保留想要的数据

  例如: 通过性别, 只对年龄进行分组

  group = df['年龄'].groupby(df['性别'])

  # 查看分组

  print(group.groups)

  # 根据分组后的名字选择分组

  print(group.get_group('F'))

  {'F': Int64Index([0, 2, 3, 6, 7], dtype='int64'), 'M': Int64Index([1, 4, 5, 8, 9], dtype='int64')}

  0 25

  2 27

  3 25

  6 25

  7 32

  Name: 年龄, dtype: int64

  代码df['年龄'].groupby(df['性别'])的逻辑是:取出df中’年龄’列数据,并且对该列数据根据df[‘性别’]列数据进行分组操作

  这个代码也可写成df.groupby(df['性别'])['年龄'], 他的逻辑是: 将df数据通过df[‘性别’]进行分组,然后再取出分组后的’年龄’列数据。两种写法达到的效果是一样的

  group.groups的结果是一个字典,字典的key是分组后每个组的名字,对应的值是分组后的数据,此方法方便我们产看分组的情况

  group.get_group('F')这个方法可以根据具体分组的名字获取,每个组的数据

  对分组进行遍历

  import pandas as pd

  df = pd.read_csv('./People.csv')

  groups = df.groupby('性别')

  # print(groups)

  for group_name,group_df in groups:

  print('分组的名称:', group_name, '分组的数据', group_df.shape)

  print('-'*10)

  分组的名称: F 分组的数据 (5, 6)

  ----------

  分组的名称: M 分组的数据 (5, 6)

  ----------

  - 将分组后的对象groups进行遍历,可以获取到group_name每个组的名字,group_df每个组的数据

  import pandas as pd

  df = pd.read_csv('./People.csv')

  groups = df.groupby('性别')

  for group_name,group_df in groups:

  f_mean = group_df['年龄'].mean()

  f_max = group_df['年龄'].max()

  f_min = group_df['年龄'].min()

  print('{}组的最大年龄是{},最小年龄是{},平均年龄是{}'.format(group_name,f_max,f_min,f_mean))

  F组的最大年龄是32,最小年龄是25,平均年龄是26.8

  M组的最大年龄是30,最小年龄是26,平均年龄是28.2

  按多列进行分组

  当需要按照多列进行分组的时候, groupby 方法里面我们传入一个列表, 列表分别存储分组依据的列名

  注意: 列表中列名的顺序, 确定了先按XXXX列分组, 然后在按照YYYY列分组, 不同的顺序产生的分组名字是不同的

  df = pd.read_csv('./People.csv')

  group=df.groupby(['性别', '婚姻状况'])

  df1 = group.size()

  print(df1)

  性别 婚姻状况

  F NO 2

  YES 3

  M NO 4

  YES 1

  dtype: int64

  group.size()返回的结果中发现索引值是多层的, 所以对于多索引值的获取, 只需要从外往里一层一层的取就可以啦, 就像我们睡觉之前,需要先脱外衣再脱掉内衣是一样的

  size = df1['F'][ 'NO']

  print(size)

  2

  pandas 常用统计函数

  count() 统计列表中非空手机开的个数

  nunique() 统计非重复的数据个数

  sum() 统计列表中所有数值的和

  mean() 计算列表中数据的平均值

  median() 统计列表中数据中位数

  max() 求列表中数据的最大值

  min() 求列表中数据的最小值

  对分组后的数据进行统计 agg()

  import pandas as pd

  df = pd.read_csv('./People.csv')

  groups = df.groupby('性别')

  for group_name,group_df in groups:

  f_se = group_df['年龄'].agg(['max','min','mean'])

  print('{}组的最大年龄是{},最小年龄是{},平均年龄是{}'.format(group_name,f_se[0],f_se[1],f_se[2]))

  F组的最大年龄是32.0,最小年龄是25.0,平均年龄是26.8

  M组的最大年龄是30.0,最小年龄是26.0,平均年龄是28.2

  在使用 agg() 函数时, 我们可以将多个统计函数一起放在一个 agg() 函数中

  如果是统计函数是pandas 提供的, 只需要将函数名字以字符串的形式存储到列表中即可

  例如: 将 max() 改成 ‘max’

  自定义统计函数

  当使用自定义的统计函数时

  先创建统计函数

  # 自定义的统计函数

  def my_peak_range(df):

  """大连人流价格 http://www.dl-byby.com/

  返回最大值与最小之间的范围

  """

  return df.max() - df.min()

  # 使用

  for group_name,group_df in groups:

  f_se = group_df['年龄'].agg(['max','min','mean',my_peak_range])

  print(f_se[0],f_se[1],f_se[3])

  32.0 25.0 7.0

  30.0 26.0 4.0

  注意: 自定义函数名字传入agg() 函数时, 不需要转换成字符串

  补充: 在这个数据中, 性别是什么的人总年龄最高

  import pandas as pd

  df = pd.read_csv('./People.csv')

  groups = df.groupby('性别')

  gende=groups.sum().sort_values(by='年龄',ascending=False).index.to_list()[0]

  """

  这行代码, 先按性别进行分组, 然后吧每组中的数据求和得到总的年龄, 在按照年龄排序

  再取出index,最后使用to_list()转换为列表,取出第一个数据

  """

  print(gende)

  M

【版权声明】本文为华为云社区用户原创内容,转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息, 否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。