У меня есть Pandas (1.0. *) Фрейм данных, который содержит запись нескольких физических переменных (например, температуры, давления и влажности). Промежуток времени между двумя записями составляет примерно 1 с, но варьируется от 0,8 до 4 с.
Я хочу рассчитать стандартное отклонение и наклон (линейной регрессии) в 5-минутном скользящем окне.
Вот как я это делаю:
import numpy as np
import pandas as pd
import datetime
np.random.seed(1)
# Build the dummy dataset for testing
rows, cols = 1000, 3
datetimes_sec = pd.date_range('2020-01-01', periods=rows, freq='1s').astype(np.int64) / 1e9
shifts = np.random.rand(rows) - 0.5 # Create random shift between -0.5s and +0.5s
datetimes = [sum(x) * 1e9 for x in zip(datetimes_sec, shifts)]
df = pd.DataFrame(np.random.rand(rows,cols),
columns=['temperature', 'pressure', 'humidity'],
index=pd.to_datetime(datetimes))
# Custom function to calculate the slope
def get_slope(series):
hours_since_epoch = series.index.astype(np.int64) / 3.6e12 # nanosecond to hour, I want the slope to be in [variable's unit] per hour
slope = np.polyfit(hours_since_epoch, series, 1)[0]
return slope
# Get the result
df = df.rolling("5min").agg(["std", get_slope])
Это работает, но слишком медленно: последняя строка занимает более 2 с для 1000 строк.
Я вижу, что мой Пользовательская функция get_slope
отвечает, если я заменю ее стандартной функцией (например, min()
), это займет 0,007 с. Но я могу найти способ сделать это быстрее.
Если невозможно получить тот же результат быстрее, обходным решением может быть пропуск некоторых строк данных: не прокручивать окно на каждой строке (т. Е. Для От 0,8 до 4 секунд), но производите вычисления только каждые 30 секунд:
- вычисляйте sd и наклон всех (~ 300) данных в период с 00:00:00 до 00: 05: 00
- рассчитать sd и наклон всех (~ 300) данных в период с 00:00:30 до 00: 05: 30
- вычислить sd и наклон всех (~ 300) данных в период с 00:01:00 до 00: 06: 00
- et c.
Вместо:
- вычислить sd и наклон всех (~ 300) данных между 00:00 : 00 и 00: 05: 00
- рассчитать sd и наклон всех (~ 300) данных в период с 00:00:01 до 00: 05: 01
- вычислить sd и наклон всех ( ~ 300) данные между 00:00:02 и 00: 05: 02
- и c.
Я не знаю, как это сделать (собственно pandas 'способ) с неравномерно расположенными данными.
Это ускорит процесс на 30, в обмен на потерю точности.