python_GroupBy高级应用_transform

38 篇文章 2 订阅

python_GroupBy高级应用_transform

分组转换和“解封”GroupBy
分组的时间重采样

Advanced GroupBy Use¶
Group Transforms and "Unwrapped" GroupBys
# 12.2 GroupBy⾼级应⽤
# 尽管我们在第10章已经深度学习了Series和DataFrame的
# # Groupby⽅法,还有⼀些⽅法也是很有⽤的。# 分组转换和“解封”GroupBy
# 在第10章,我们在分组操作中学习了apply⽅法,进⾏转换。还
# 有另⼀个transform⽅法,它与apply很像,但是对使⽤的函数有
# ⼀定限制:
# 它可以产⽣向分组形状⼴播标量值
# 它可以产⽣⼀个和输⼊组形状相同的对象
# 它不能修改输⼊
# 来看⼀个简单的例⼦:
​
df = pd.DataFrame({'key': ['a', 'b', 'c'] * 4,
                   'value': np.arange(12.)})
df.head()
key	value
0	a	0.0
1	b	1.0
2	c	2.0
3	a	3.0
4	b	4.0
g = df.groupby('key').value
g.mean()
key
a    4.5
b    5.5
c    6.5
Name: value, dtype: float64
假设我们想产⽣⼀个和df['value']形状相同的Series,但值替换为
# 按键分组的平均值。我们可以传递函数lambda x: x.mean()进⾏
# 转换:
# 假设我们想产⽣⼀个和df['value']形状相同的Series,但值替换为
# 按键分组的平均值。我们可以传递函数lambda x: x.mean()进⾏
# 转换:
g.transform(lambda x: x.mean())
0     4.5
1     5.5
2     6.5
3     4.5
4     5.5
5     6.5
6     4.5
7     5.5
8     6.5
9     4.5
10    5.5
11    6.5
Name: value, dtype: float64
对于内置的聚合函数,我们可以传递⼀个字符串假名作为
# GroupBy的agg⽅法:
# 对于内置的聚合函数,我们可以传递⼀个字符串假名作为
# GroupBy的agg⽅法:
g.transform('mean')
0     4.5
1     5.5
2     6.5
3     4.5
4     5.5
5     6.5
6     4.5
7     5.5
8     6.5
9     4.5
10    5.5
11    6.5
Name: value, dtype: float64
与apply类似, transform的函数会返回Series,但是结果必须与
# 输⼊⼤⼩相同。举个例⼦,我们可以⽤lambda函数将每个分组
# 乘以2:
# 与apply类似, transform的函数会返回Series,但是结果必须与
# 输⼊⼤⼩相同。举个例⼦,我们可以⽤lambda函数将每个分组
# 乘以2:
g.transform(lambda x: x * 2)
0      0.0
1      2.0
2      4.0
3      6.0
4      8.0
5     10.0
6     12.0
7     14.0
8     16.0
9     18.0
10    20.0
11    22.0
Name: value, dtype: float64
再举⼀个复杂的例⼦,我们可以计算每个分组的降序排名:
# 再举⼀个复杂的例⼦,我们可以计算每个分组的降序排名:
g.transform(lambda x: x.rank(ascending=False))
0     4.0
1     4.0
2     4.0
3     3.0
4     3.0
5     3.0
6     2.0
7     2.0
8     2.0
9     1.0
10    1.0
11    1.0
Name: value, dtype: float64
看⼀个由简单聚合构造的的分组转换函数:
# 看⼀个由简单聚合构造的的分组转换函数:
def normalize(x):
    return (x - x.mean()) / x.std()
# 我们⽤transform或apply可以获得等价的结果:
g.transform(normalize)
g.apply(normalize)
0    -1.161895
1    -1.161895
2    -1.161895
3    -0.387298
4    -0.387298
5    -0.387298
6     0.387298
7     0.387298
8     0.387298
9     1.161895
10    1.161895
11    1.161895
Name: value, dtype: float64
解封分组操作可能包括多个分组聚合,但是⽮量化操作还是会带
# 来收益。
# 内置的聚合函数,⽐如mean或sum,通常⽐apply函数快,也⽐
# transform快。这允许我们进⾏⼀个所谓的解封(unwrapped)分
# 组操作:
g.transform('mean')
normalized = (df['value'] - g.transform('mean')) / g.transform('std')
normalized
# 解封分组操作可能包括多个分组聚合,但是⽮量化操作还是会带
# 来收益。
0    -1.161895
1    -1.161895
2    -1.161895
3    -0.387298
4    -0.387298
5    -0.387298
6     0.387298
7     0.387298
8     0.387298
9     1.161895
10    1.161895
11    1.161895
Name: value, dtype: float64



### Grouped Time Resampling
import pandas as pd
# 分组的时间重采样
# 对于时间序列数据, resample⽅法从语义上是⼀个基于内在时间
# 的分组操作。下⾯是⼀个示例表:
N = 15
times = pd.date_range('2017-05-20 00:00', freq='1min', periods=N)
df = pd.DataFrame({'time': times,
                   'value': np.arange(N)})
df
# 这⾥,我们可以⽤time作为索引,然后重采样:
df.set_index('time').resample('5min').count()
value
time	
2017-05-20 00:00:00	5
2017-05-20 00:05:00	5
2017-05-20 00:10:00	5
# 假设DataFrame包含多个时间序列,⽤⼀个额外的分组键的列进
# ⾏标记:
df2 = pd.DataFrame({'time': times.repeat(3),
                    'key': np.tile(['a', 'b', 'c'], N),
                    'value': np.arange(N * 3.)})
df2[:7]
time	key	value
0	2017-05-20 00:00:00	a	0.0
1	2017-05-20 00:00:00	b	1.0
2	2017-05-20 00:00:00	c	2.0
3	2017-05-20 00:01:00	a	3.0
4	2017-05-20 00:01:00	b	4.0
5	2017-05-20 00:01:00	c	5.0
6	2017-05-20 00:02:00	a	6.0
time_key = pd.TimeGrouper('5min')
resampled = (df2.set_index('time')
             .groupby(['key', time_key])
             .sum())
resampled
resampled.reset_index()

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值