Решайте более сложные проблемы с меньшими затратами инженеров

Цель этой статьи и обзора статьи

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

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

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

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

Пример проблемы

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

Другие функции, которые могут быть полезны:

  • Финансовые отчеты компании
  • Макроэкономические данные
  • Отраслевые тенденции
  • Показатели конкурентов

Из прошлого опыта мы знаем, что хотели бы:

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

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

Обзор фреймворка

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

Типы узлов:

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

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

Вот как может выглядеть разбивка расчета чистой прибыли:

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

Требования высокого уровня

  1. Декларативное и тестируемое определение графа
  2. Ленивая обработка графиков, пересчет только недостающих функций
  3. Легкость определения новых типов вычислений
  4. Функции поддержки и метаданные функциональных блоков
  5. Поддержка временных рядов и реляционной природы данных
  6. [ML] встроены в перекрестную проверку и стек.

Декларативное определение вычислительного графа

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

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

  1. Имя класса, который будет обрабатывать эту единицу работы - Extractor
  2. Зависимости, которые необходимо вычислить, если они еще не доступны - Входные функции
  3. Названия групп функций, над которыми нужно работать

Вот пример такого объявления узла, который вычисляет относительный рост для всех функций в группе функций:

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

Вычисление, требующее обучения машинному обучению, представлено немного другим блоком, который требует ряда дополнительных параметров:

  1. Заводское название модели
  2. Параметры модели
  3. Имя целевой переменной

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

Отделение объявления графа от контекста выполнения позволяет автоматизировать тестирование и создание конфигурации.

Обработка графиков

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

Типы вычислительных шагов

Поставщики данных - вводят в систему разные типы данных. Примеры провайдеров:

  1. Особенности, характерные для компании - стоимость акций, квартальные отчеты
  2. Данные по стране - Инфляция, ВВП

Унарная операция над функциями

  1. Вычисления в скользящем окне. Пример - расчет скользящей средней
  2. Timeshift

Двоичные операции - объедините 2 функции по времени и ключу и выполните математическую операцию:

  1. Присоединяйтесь и вычитайте. Пример использования - получение операционной прибыли путем вычитания затрат из выручки
  2. Присоединяйся и разделяй. Пример использования - объединение доходов со сдвигом доходов во времени для определения роста.
  3. Присоединяйся и умножайся. Пример использования - объедините прошлый доход с прогнозом роста, чтобы получить будущий доход.

Другие типы этапов обслуживания

  1. Выберите N лучших прогнозов по функциям
  2. Расчет показателей качества прогнозов для анализа

Реализуя такие базовые блоки и затем объединяя их в структуры более высокого уровня, можно определить довольно сложную логику. Каждый тип экстрактора функций - это класс, реализующий общий интерфейс, зарегистрированный в компоненте, отвечающем за вычисление функций, и на который ссылается Graph по имени.

Метаданные функций

Также удобно хранить метаданные, связанные с функциями - какие прямые родители этой функции, если это будущий прогноз, тип объекта и т. Д.

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

Поддержка временных рядов и реляционной природы данных

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

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

Например, ежедневные изменения цены акций будут индексироваться по дням и группироваться по тикеру (идентификатор компании).

Описание и примеры блоков:

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

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

Последовательная ориентация функций

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

Вот пример квартальной выручки и стоимости выручки Microsoft, преобразованной из плоской:

к последовательному представлению:

Чтобы предотвратить утечку информации о будущих событиях в модель ML, все последовательные функции, имеющие в своих метаданных Seq 0 и не являющиеся прогнозами, отфильтровываются из представления функций, которое передается в модель.

Обучение моделей машинного обучения

Фреймворк не зависит от специфики различных моделей машинного обучения, все, что требуется, - это реализовать стандартный интерфейс. Режим обучения по умолчанию - это обучение и прогнозирование скольжения во времени, в течение которого модель обучается на прошлых событиях {0: t-1} для прогнозирования будущих событий {t}. После того, как все прогнозы для периода {t} выполнены, данные обучения расширяются до {0: t} и снова обучаются для прогнозирования {t + 1}.

Обучение для каждого временного шага разбивается на k-кратные, с набором задержек, используемым для обнаружения ранней точки остановки (для древовидных моделей) и выбора гиперпараметров:

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

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

Укладка достигается последовательностью различных моделей одна за другой.

Оценка результатов и анализ ошибок

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

  1. Повышение точности прогнозов по сравнению с другими моделями
  2. Интервалы прогнозирования
  3. Анализ остатков
  4. Проверка автокорреляции
  5. Проверка нормального распределения
  6. Проверка смещения

Работа в процессе

Автоматизированное построение графа

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

Адаптировать решение для работы на нескольких машинах

Части фреймворка, которые выглядят легко распараллеливаемыми:

  1. Обработка изолированных частей графа
  2. Иерархические характеристики - мы можем вычислить характеристики компании A отдельно от характеристик компании B.
  3. Временные особенности

Удалось ли нам повысить точность?

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

Ответ - да, для всех прогнозируемых переменных есть довольно значительное повышение точности.

Вот сравнение прогноза дохода для случайной компании (в данном случае ROST) между замечательной библиотекой Prophet и одним из прогнозов модели конвейера:

Прогноз доходов другой случайной компании, EBAY

Заключение

Несмотря на то, что первоначальное вложение является довольно значительным, наличие структуры, аналогичной описанной, приводит к:

  1. Меньше времени на выполнение каждого эксперимента - ›Проверка -› Цикл интеграции
  2. Меньше времени на исправление ошибок и написание тестов
  3. Целостный взгляд на влияние различных моделей, гиперпараметров и функций на окончательный прогноз
  4. Меньше времени тратится на воспроизведение прошлых экспериментов

Это решение постепенно эволюционировало от автоматизации и улучшения повседневной деятельности. В случае необходимости реализовать такую ​​структуру с нуля, я также рассмотрел бы возможность построения на основе существующих технологий с открытым исходным кодом, например, https://airflow.apache.org

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