pandas/numpy - 基于时间的平均值

Posted

技术标签:

【中文标题】pandas/numpy - 基于时间的平均值【英文标题】:pandas/numpy - time based averages 【发布时间】:2021-11-19 10:33:02 【问题描述】:

我有一些数据基本上是一个日期时间戳和一个值,例如:

01-01-2021 11:40:01,   1.0532
01-01-2021 11:40:02,   1.0531
...
01-01-2021 11:41:01,   1.0541
01-01-2021 11:41:01,   1.0542

有很多数据。我想知道是否有办法让 pandas 或 numpy 快速计算时间增量(例如 1 秒、5 秒、1 分钟、5 分钟等)的平均值。

我知道有一些函数可以计算多个点的平均值,但它需要超过我需要的时间增量,即 1 秒平均值、5 秒平均值、1 分钟平均值等。

谢谢

标记

【问题讨论】:

【参考方案1】:

让我们首先获取一些看起来像您描述的随机数据:

>>> df = pd.DataFrame(
...     'datetime': pd.date_range(pd.Timestamp.today(), periods=2048, freq='300ms'),
...     'value': np.random.randint(0, 100, 2048) / 200 + 1
... )

如果您的 datetime 是字符串而不是实际的日期时间,您应该先转换它们:

>>> df['datetime'] = pd.to_datetime(df['datetime'])

然后您可以使用pd.Grouper 来实现您想要的。例如每秒:

>>> df.groupby(pd.Grouper(key='datetime', freq='1s'))['value'].mean()
datetime
2021-09-27 11:07:15    1.190000
2021-09-27 11:07:16    1.180000
2021-09-27 11:07:17    1.141250
2021-09-27 11:07:18    1.285000
2021-09-27 11:07:19    1.190000
                         ...   
2021-09-27 11:17:25    1.255000
2021-09-27 11:17:26    1.305000
2021-09-27 11:17:27    1.150000
2021-09-27 11:17:28    1.258333
2021-09-27 11:17:29    1.312500
Freq: S, Name: value, Length: 615, dtype: float64

每 5 秒:

>>> df.groupby(pd.Grouper(key='datetime', freq='5s'))['value'].mean()
datetime
2021-09-27 11:07:15    1.194286
2021-09-27 11:07:20    1.267647
2021-09-27 11:07:25    1.305000
2021-09-27 11:07:30    1.223125
2021-09-27 11:07:35    1.255294
                         ...   
2021-09-27 11:17:05    1.280882
2021-09-27 11:17:10    1.225294
2021-09-27 11:17:15    1.329687
2021-09-27 11:17:20    1.278235
2021-09-27 11:17:25    1.262353
Freq: 5S, Name: value, Length: 123, dtype: float64

等,见reference of frequency expressions。

另外请注意,您的平均值可能并不总是在每个单位时间内具有相同数量的值:

>>> df.groupby(pd.Grouper(key='datetime', freq='1s'))['value'].count()
datetime
2021-09-27 11:07:15    1
2021-09-27 11:07:16    3
2021-09-27 11:07:17    4
2021-09-27 11:07:18    3
2021-09-27 11:07:19    3
                      ..
2021-09-27 11:17:25    3
2021-09-27 11:17:26    4
2021-09-27 11:17:27    3
2021-09-27 11:17:28    3
2021-09-27 11:17:29    4
Freq: S, Name: value, Length: 615, dtype: int64

【讨论】:

感谢您的回答,这不是我所追求的。我假设 Grouper,组的日期时间为最接近的秒或分钟。理想情况下,我想要最后 5 分钟的内容,因此 17:06:14 将包括回到 17:01:14 的记录。我错了吗?谢谢 @MarkyMark1000 它不会对 afaik 进行舍入,而是将其分类。你想要一个滚动平均值,即与输入相同数量的输出?或者你只是想改变垃圾箱的原点,以便最后一个在当前时间之前? 感谢您的回复。我希望平均值超过最后 5 分钟的数据。如果它不可用,请不要担心,我只是想知道是否有一个系统来计算它。我直接在python中试了一下,速度非常非常慢。看起来我将不得不存储数据或在一定数量的步骤上使用滚动平均值。谢谢 我的意思是如果你只想要最后5分钟,你可以使用df.loc[pd.Timestamp.today() - pd.Timedelta(minutes=5):].mean()

以上是关于pandas/numpy - 基于时间的平均值的主要内容,如果未能解决你的问题,请参考以下文章

PostgreSQL 中基于时间戳的移动平均线

基于星期几的平均值

基于不规则时间序列数据计算规则周期平均值的最佳方法

numpy pandas1

基于不同日期的红移滚动平均值

使用 pandas/dataframe 基于 2 列计算加权平均值