Здесь я собираю данные за 17 сезонов НХЛ, начиная с сезона 2005–2006 гг. и заканчивая сезоном 2021–2022 гг. Я извлекаю данные непосредственно с nhl.com, используя методы парсинга (хотя есть масса сайтов получше, с которых можно получить игровые данные). Я очищаю данные и извлекаю особенности из индивидуальной работы каждой команды. Я рассчитываю скользящее среднее/сумму нескольких статистических данных для нескольких разных периодов времени и сравниваю их с той же статистикой их оппонентов для каждой игры.

В качестве отправной точки для моих результатов, команда хозяев выиграла 8249 из 16843 игр за период времени, за который взяты мои данные. Таким образом, если бы кто-то предсказал, что домашняя команда выиграет каждую игру в наборе данных, его точность составила бы 48,98%. Моя лучшая модель достигает точности 57,39%.

Предыдущие выводы

В литературе точность 61,54% была достигнута Gianni Pischedda из soccerlogic.com с помощью ClusteR, программного обеспечения, разработанного для спортивного анализа. Об этих результатах можно прочитать здесь.

В аналогичном проекте пользователь GitHub kn-kn смог предсказать результаты игр НХЛ с точностью от 53% до 58%, используя деревья решений и случайные леса и различные типы комбинаций атрибутов данных.

В своем анализе я использую три различные распространенные модели машинного обучения: логистическую регрессию, классификацию случайного леса и линейный SVM. До сих пор наилучшие результаты были достигнуты с использованием логистической регрессии с точностью 57,3%.

Очистка данных и создание функций

Ниже представлен DataFrame, с которым мне предстояло работать после чтения данных в Python и первоначальной очистки данных:

В DataFrame каждая строка представляет одну игру; однако, как вы можете видеть при просмотре, для каждой игры есть два отдельных наблюдения — по одному для каждой игры. Единственный способ определить, кто был командой хозяев, а кто командой гостей, — использовать столбец «идентификатор». Если идентификатор «против», то команда в столбце «команда» является командой гостей. Если «@», то команда в столбце «команда» является командой гостей. Чтобы получить данные так, как я хотел, я решил разделить DataFrame на отдельные команды, что потребовало создания 33 отдельных DataFrame для расчета статистики. Хотя это было неэффективно, в основном это был вопрос копирования и вставки кода, который я уже написал кучу раз. Оглядываясь назад, я мог бы написать функцию, чтобы избежать копирования и вставки, но я понятия не имел, чем я занимался в то время.

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

  • точки
  • цели
  • голы против
  • мощность играть %
  • пенальти убийство %
  • удары по воротам
  • выстрелы против
  • % побед вбрасывания
  • сохранять %

Я рассчитываю среднее значение всех этих статистических данных за три различных периода времени: короткое окно, среднее окно и длинное окно времени. Для моделей машинного обучения я решил поэкспериментировать с длительностью каждого временного окна. Ниже приведены различные комбинации, которые я использую для своих моделей:

После того, как это было сделано для каждой команды, каждый DataFrame был объединен в один более крупный DataFrame.

Но в этот момент вы можете сказать что-то вроде «Колтон, после этого каждая игра все еще имеет две колонки, которые ее представляют. Почему вы так мучаете нас?!

Почему да, это довольно хороший момент.

Чтобы исправить это, я разделил DataFrame снова на DataFrames домашней и выездной команд. Эти два они объединены на основе даты противника. Наконец, у нас есть DataFrame, который

a) содержит нужные нам данные

и

b) содержит одну строку, представляющую каждую игру

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

Применение различных алгоритмов машинного обучения

Прежде чем применять различные алгоритмы, я изначально отложил 30% данных для использования в качестве тестовых данных. Остальные 70% будут данными, используемыми для обучения наших моделей.

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

Логистическая регрессия

Логистическая регрессия — хороший начальный алгоритм при выборе между двумя вещами. В этом случае мы будем предсказывать, выиграет ли команда хозяев (1) или проиграет (0).

Данные были обучены на данных обучения, а результаты, основанные на тестировании на данных тестирования, приведены ниже.

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

Судя по матрице путаницы, алгоритм логистической регрессии более эффективен при прогнозировании результатов домашних поражений (точность ~ 60% глазного яблока), чем домашних побед (точность ~ 53%). Из статистики точности временные окна (15, 25, 40) лучше всего подходят для использования в скользящей статистике в нашем наборе данных. Однако временные окна (10, 18, 30) имеют наилучшую общую производительность с точки зрения статистики производительности.

Что хорошего в модели логистической регрессии, так это то, что ее легко и просто обучать, в отличие от более сложных моделей машинного обучения. Давайте посмотрим на пару других.

Случайный лесной классификатор

Ниже показаны результаты регрессора случайного леса, обученного на обучающем наборе. Максимальная глубина дерева была установлена ​​на 5, а количество оценщиков — на 200. Для получения лучших результатов при использовании случайных лесов я мог бы рассмотреть возможность использования поиска по сетке для поиска оптимальных параметров в будущем. Но пока я не слишком беспокоюсь. По моему мнению, дальнейшее улучшение будет больше зависеть от качества данных.

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

Как и предыдущая модель, наша модель имеет самую высокую точность при использовании скользящей статистики, основанной на временных окнах (15, 25, 40).

Линейный метод опорных векторов

Последним алгоритмом, который я решил протестировать, был линейный классификатор SVM. Ниже показаны результаты тестового набора.

Забавно, но мы получаем точно такой же график для матрицы путаницы, как и для логистической регрессии. Эта модель хорошо работает с реальными проигрышами дома и плохо с реальными выигрышами дома. Наивысшая точность была достигнута с использованием оконных временных рамок (20, 40, 60), едва вытеснив победителя из двух других алгоритмов, (15, 25, 40) скользящих статистических временных рамок.

Выводы

Я протестировал некоторые базовые алгоритмы машинного обучения почти на 17 000 игр НХЛ, сыгранных в период с 2005 по 2022 год. Я добился максимальной точности 57,39%, используя модель логистической регрессии со скользящим статистическим периодом 15 игр, 25 игр и 40 игр, чтобы сравнить статистику между две противоборствующие команды.

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

В целом, я обнаружил, что предсказывать результаты между командами НХЛ довольно сложно. Хоккей традиционно является малорезультативной игрой, и результаты команды нельзя предсказать исключительно на основе их соперников и статистики из предыдущих игр. Эта модель не учитывает такие вещи, как травмы, личные истории игроков, дисквалификации, командные рейтинги и многое другое. Короче говоря, делать прогнозы на матчи НХЛ сложно.

Все, что я здесь использую, доступно в репозитории GitHub здесь.

Первоначально опубликовано на https://cbarger.com 6 июня 2022 г.