Частота в pandas индексе таймсерий и статистической модели - PullRequest
2 голосов
/ 19 июня 2020

У меня есть pandas таймсерий y, который плохо работает с функциями statsmodel.

import statsmodels.api as sm

y.tail(10)

2019-09-20     7.854
2019-10-01    44.559
2019-10-10    46.910
2019-10-20    49.053
2019-11-01    24.881
2019-11-10    52.882
2019-11-20    84.779
2019-12-01    56.215
2019-12-10    23.347
2019-12-20    31.051
Name: mean_rainfall, dtype: float64

Я проверяю, что это действительно таймсерий

type(y)
pandas.core.series.Series

type(y.index)
pandas.core.indexes.datetimes.DatetimeIndex

Отсюда я могу без проблем передавать таймсерию через функцию автокорреляции, которая дает ожидаемый результат

plot_acf(y, lags=72, alpha=0.05)

Однако, когда я пытаюсь передать тот же самый объект y в SARIMA

mod = sm.tsa.statespace.SARIMAX(y.mean_rainfall, order=pdq, seasonal_order=seasonal_pdq)
results = mod.fit()

, я получаю следующую ошибку:

Дата index был предоставлен, но он не имеет связанной информации о частоте и поэтому будет проигнорирован, например, при прогнозировании.

Проблема в том, что частота моих временных рядов не является регулярной (это 1, 10, и 20 числа каждого месяца), поэтому я не могу установить, например, freq='m' или freq='D'. Какое решение в этом случае?

Я новичок в использовании таймсерий, мне помогут любые советы о том, как не игнорировать мой индекс во время прогнозирования. Это предотвращает возможность любых прогнозов

Ответы [ 2 ]

0 голосов
/ 19 июня 2020

Прежде всего, чрезвычайно важно понять, какова связь между столбцом datetime и целевым столбцом (дождем). Глядя на предоставленный вами фрагмент, я могу думать о двух возможностях:

  1. y представляет количество осадков, которые произошли в диапазоне дат между датой текущей строки и датой следующей строки. Если это так, то временные ряды представляют собой агрегированные ряды осадков с неравными периодами дат, например 1-10, 10-20, 20- (конец месяца). Если это так, у вас есть два варианта:
    • Вы можете дезагрегировать свои данные, используя либо равный вес, либо, что еще лучше, интерполяцию для создания непрерывных и относительно гладких временных рядов. Затем вы можете подогнать свою модель к ежедневным временным рядам и создать прогнозы, которые, естественно, также будут ежедневными по своей природе. Их можно объединить обратно в периоды 1–10, 10–20, 20- (на конец месяца), чтобы получить свои прогнозы. Один из способов выполнить повторную выборку - использовать приведенный ниже код.
ts.Date = pd.to_datetime(ts.Date, format='%d/%m/%y')
ts['delta_time'] = (ts['Date'].shift(-1) - ts['Date']).dt.days
ts['delta_rain'] = ts['Rain'].shift(-1) - ts['Rain']
ts['timesteps'] = ts['Date']
ts['grad_rain'] = ts['delta_rain'] / ts['delta_time']
ts.set_index('timesteps', inplace=True )
ts = ts.resample('d').ffill()
ts

enter image description here

ts['daily_rain'] = ts['Rain'] + ts['grad_rain']*(ts.index - ts['Date']).dt.days
ts['daily_rain'] = ts['daily_rain']/ts['delta_time']
print(ts.head(50))

enter image description here

daily_rain теперь является целевым столбцом, а index т.е. timesteps - это временная метка.

  • Другой вариант - вы приблизите что диапазон дат 1-10, 10-20, 20- (EOM) составляет примерно 10 дней, так что это действительно равные временные интервалы. Конечно, statsmodel не позволит этого, поэтому вам нужно будет сбросить индекс, чтобы имитировать datetime, для которого вы поддерживаете сопоставление. Ниже показано, что вы используете в статистической модели как y, но сохраняете сопоставление с вашими исходными датами. Freq будет 'd' или 'daily', и вам также нужно будет изменить масштаб сезонности, чтобы он соответствовал новой шкале дат.
y.tail(10)

2019-09-01    7.854
2019-09-02    44.559
2019-09-03    46.910
2019-09-04    49.053
2019-09-05    24.881
2019-09-06    52.882
2019-09-07    84.779
2019-09-08    56.215
2019-09-09    23.347
2019-09-10    31.051
Name: mean_rainfall, dtype: float64

Я бы порекомендовал первый вариант, хотя он просто больше точный по своей природе. Также вы можете опробовать другие уровни агрегирования во время обучения модели, а также для своих прогнозов. Больше контроля!

Второй сценарий заключается в том, что данные представляют собой измерения только для самой даты, а не для диапазона. Это означало бы, что технически у вас сейчас недостаточно информации для построения точных временных рядов - ваши временные интервалы не равноудалены, и у вас недостаточно информации о том, что произошло между временными шагами. Однако вы все равно можете импровизировать и получить некоторые приближения. Второй подход, перечисленный выше, будет работать как есть. Для первого подхода вам нужно будет выполнить интерполяцию, но, учитывая, что целевая переменная, то есть количество осадков, и количество осадков имеет много вариаций, я бы очень отговаривал это !!
0 голосов
/ 19 июня 2020

Как я вижу, пакет использует частоту как предпосылку для всего, поскольку это проблема временного ряда. Таким образом, вы не сможете использовать его с данными разных частот. Фактически, вам придется сделать предположение, чтобы ваш анализ соответствовал вашим данным для использования. Вот некоторые варианты:

1) Рассмотрите 3 разных анализа (1-й, 10-й, 20-й дни по отдельности) и используйте частоту 30 дней.

2) Поскольку у вас есть ~ 10d равно разделенных данных, вы можно рассмотреть возможность использования какой-либо интерполяции, а затем выполнить понижающую дискретизацию до частоты 1d. Конечно, этот вариант имеет смысл только в зависимости от характера вашей проблемы и того, как быстро изменяются ваши данные.

В любом случае, я просто хотел бы указать, что то, как вы моделируете свою проблему и свои данные, является ключевым моментом при работе с временными рядами и наукой о данных в целом. По моему опыту как специалист по данным, я могу сказать, что анализируя область (откуда пришли ваши данные), вы можете почувствовать, какой подход будет работать лучше.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...