Крос-валідація часових рядів

Machine Learning для часових рядів у Python

Chris Holdgraf

Fellow, Berkeley Institute for Data Science

Крос-валідація в scikit-learn

# Ітерація методом "split" повертає індекси train/test
for tr, tt in cv.split(X, y):
    model.fit(X[tr], y[tr])
    model.score(X[tt], y[tt])
Machine Learning для часових рядів у Python

Типи крос-валідації: KFold

  • Крос-валідація KFold ділить дані на кілька «складань» однакового розміру
  • Це один із найпоширеніших способів крос-валідації

      from sklearn.model_selection import KFold
      cv = KFold(n_splits=5)
      for tr, tt in cv.split(X, y):
          ...
    
Machine Learning для часових рядів у Python

Візуалізація прогнозів моделі

fig, axs = plt.subplots(2, 1)

# Відобразити індекси, вибрані для валідації на кожній ітерації
axs[0].scatter(tt, [0] * len(tt), marker='_', s=2, lw=40)
axs[0].set(ylim=[-.1, .1], title='Test set indices (color=CV loop)', 
           xlabel='Index of raw data')

# Відобразити прогноз моделі на кожній ітерації
axs[1].plot(model.predict(X[tt]))
axs[1].set(title='Test set predictions on each CV loop', 
           xlabel='Prediction index')
Machine Learning для часових рядів у Python

Візуалізація поведінки KFold CV

Machine Learning для часових рядів у Python

Заувага щодо перетасовування даних

  • Багато ітераторів CV дозволяють перетасовувати дані під час крос-валідації.
  • Це працює лише для i.i.d. даних, а часові ряди зазвичай такими не є.
  • Не слід перетасовувати дані, коли будуєте прогнози для часових рядів.

      from sklearn.model_selection import ShuffleSplit
    
      cv = ShuffleSplit(n_splits=3)
      for tr, tt in cv.split(X, y):
          ...
    
Machine Learning для часових рядів у Python

Візуалізація поведінки з перетасовуванням у CV

Machine Learning для часових рядів у Python

Використання ітератора CV для часових рядів

  • Дотепер ми порушували лінійний плин часу під час крос-валідації
  • Однак зазвичай не слід використовувати майбутні точки для передбачення минулого
  • Підхід: завжди беріть тренувальні дані з минулого, щоб прогнозувати майбутнє
Machine Learning для часових рядів у Python

Візуалізація ітераторів крос-валідації для часових рядів

# Імпортувати та ініціалізувати ітератор крос-валідації
from sklearn.model_selection import TimeSeriesSplit
cv = TimeSeriesSplit(n_splits=10)

fig, ax = plt.subplots(figsize=(10, 5))
for ii, (tr, tt) in enumerate(cv.split(X, y)):
    # Показати індекси тренування й тесту
    l1 = ax.scatter(tr, [ii] * len(tr), c=[plt.cm.coolwarm(.1)], 
                    marker='_', lw=6)
    l2 = ax.scatter(tt, [ii] * len(tt), c=[plt.cm.coolwarm(.9)], 
                    marker='_', lw=6)
    ax.set(ylim=[10, -1], title='TimeSeriesSplit behavior', 
           xlabel='data index', ylabel='CV iteration')
    ax.legend([l1, l2], ['Training', 'Validation'])
Machine Learning для часових рядів у Python

Візуалізація ітератора TimeSeriesSplit

Machine Learning для часових рядів у Python

Власні функції оцінювання в scikit-learn

def myfunction(estimator, X, y):
    y_pred = estimator.predict(X)
    my_custom_score = my_custom_function(y_pred, y)
    return my_custom_score
Machine Learning для часових рядів у Python

Власна функція кореляції для scikit-learn

def my_pearsonr(est, X, y):
    # Згенерувати прогнози та перетворити на вектор 
    y_pred = est.predict(X).squeeze()

    # Використати функцію numpy "corrcoef" для обчислення кореляційної матриці
    my_corrcoef_matrix = np.corrcoef(y_pred, y.squeeze())

    # Повернути одне значення кореляції з матриці
    my_corrcoef = my_corrcoef[1, 0]
    return my_corrcoef
Machine Learning для часових рядів у Python

Давайте потренуємось!

Machine Learning для часових рядів у Python

Preparing Video For Download...