python - 滚动时间窗口中值(value)的分组百分位数排名

标签 python pandas pandas-groupby rolling-computation percentile

在这些样本数据中,用户在随机日期及时下了某些随机值的订单。 我已经成功实现了一种方法来计算同一用户过去 180 天订单中每个值的百分位数排名。

但是,对于较大的 n 值,最后一个 groupby 行代码运行速度非常慢(1M 行运行大约 1 分 30 秒)有没有人对如何改进有建议计算时间?

import pandas as pd
import numpy as np
from scipy.stats import percentileofscore

#percentile rank function
def rank(x, kind):
    return percentileofscore(x, score = x.iloc[-1], kind = kind)

#sample data
n = 10000
orders = pd.DataFrame({
    'user':np.random.randint(1, 100, size = n),
    'value':np.random.randn(n),
    'date':np.random.choice( pd.date_range('1/1/2019', periods=730,
                          freq='D'), n)
    })

orders_sort = orders.sort_values(by = ['user', 'date']).reset_index(drop =True)

#group by time window percentile rank - SLOW!
orders_sort.groupby('user')[['value', 'date']].rolling('180d', on = 'date').apply(lambda x: rank(x, kind = 'mean'))

               value       date
user
1    0     50.000000 2019-01-03
     1     75.000000 2019-01-10
     2     83.333333 2019-01-12
     3     87.500000 2019-01-17
     4     10.000000 2019-01-22
...              ...        ...
99   9995  19.565217 2020-11-23
     9996  64.583333 2020-11-26
     9997  39.583333 2020-12-04
     9998  54.000000 2020-12-05
     9999   6.000000 2020-12-12

[10000 rows x 2 columns]

最佳答案

您可以利用 apply 中的参数 raw=True 来传递 numpy 数组而不是 Series。您需要稍微更改您的函数才能使用数组。

def rank_np(x, kind):
    return percentileofscore(x, score = x[-1], kind = kind) #no iloc as x is an array

然后就像您使用参数 raw 所做的那样:

orders_sort.groupby('user')[['value', 'date']]\
  .rolling('180d', on = 'date')\
  .apply(lambda x: rank_np(x, kind = 'mean'), raw=True) #see here

当 n=10K 或 50K 时,速度提高了 6.5 倍,但不确定 n=1M 行时的表现如何

关于python - 滚动时间窗口中值(value)的分组百分位数排名,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/70746713/

相关文章:

python - 过滤 Blaze 表中的日期

python - 在 Debian 服务器上使用 PyQt4.QtWebKit

python - 训练 Keras 序列模型时损失没有减少

python - Pandas 数据帧 : how to turn one row into separate rows based on labelled column value

python - 如何为 keras 中的 LSTM 回归准备输入数据?

python - 来自 groupby 的 Pandas 累积差异

python - 从正在读取的文件列表中删除 '\n' 列表项

python - 根据另一个数据帧的值获取数据帧的子集 (Python)

Python,计算另一列中值的出现频率

python - 将Groupby函数应用于python中的多列并计算