В какой-то момент я переведу текст ниже на английский язык и он будет в этом месте.
Градиентный спуск... Вы можете спросить меня "Зачем изобретать велосипед?". Поэтому, для начала, хотелось бы сказать зачем этот проект нужен лично мне. В какой-то момент я решил заняться ML и градиент занимает здесь одно из главных мест. После первого собеседования в VK, я понял, что не до конца понимаю что это вообще такое и решил разобраться. После небольшого катарсиса я сел пописать код ручками (чтобы лучше усвоилось) и теперь делюсь результатами. Возможно, у кого-то возникают схожие с моими вопросы; поэтому, надеюсь, моя работа кому-то поможет.
В этом блоке я вкратце опишу суть метода и поясню в какой момент в моей голове произошла нестыковка.
Пусть даны объекты
Нужно построить модель
Коэффициенты
В таком случае
Существуют различные функции потерь (
Основные метрики в задачах регрессии:
- Mean Absolute Error (MAE)
$= \frac{1}{n} \ast \sum |y_i - y_i^*|$ - Mean Absolute Percentage Error (MAPE)
$= \frac{1}{n} \ast \sum |\frac{y_i - y_i^*}{y_i}|$ - Mean Squared Error (MSE)
$= \frac{1}{n} \ast \sum (y_i - y_i^*)^2$ - Root Mean Squared Error (RMSE)
$= \sqrt{\frac{1}{n} \ast \sum (y_i - y_i^*)^2}$
Теперь вспомним, что градиент функции в точке - это вектор, показывающий направление наибольшего возрастания функции в данной точке.
Суть метода в том, чтобы считать градиент функции потерь и идти в обратном направлении (в сторону антиградиента), что позволит приблизиться к точке минимума функции потерь.
А теперь вспомним что этого мы и хотим: найти такие коэффициенты
Градиент считается как вектор частных производных функции по всем аргументам.
В этот момент и возникла нестыковка. Изначально, мне сразу в голову приходила наша функция
А теперь стоит рассказать как дело обстоит на самом деле. Для этого рассмотрим самый простой пример, который может быть.
Допустим, у нас есть одна точка
Допустим, мы находимся на каком-то промежуточном шаге и получили коэффициенты
Теперь поймем, что мы хотим уменьшить
Можно нарисовать плоскость, на осях которой будут значения
Для примера с одной точкой подходит рисунок ниже:
Здесь прямая - это наши решения при поиске нужных коэффициентов. Поверхность функции потерь принимает такую форму, что в любом сечении, перпендикулярном нашей прямой, будет парабола.
Если взять любую точку на прямой,
По сути, мы будем на каждом шаге строить градиент функции потерь в пространстве параметров модели и спускаться постепенно к ее минимуму. Именно этого понимания мне не хватало раньше.
Каким образом будем спускаться? Вычитая из каждого коэффициента соответствующий элемент градиента.
Однако, чтобы не перескочить через точку минимума, вводят дополнительный коэффициент
Поняв как это работает для одной точки, добавим еще одну.
Теперь для каждой точки подходящие коэффициенты
Пример представлен на рисунке ниже:
Красной линией здесь показан процесс градиентного спуска (корректировки коэффициетов для уменьшения значения функции потерь).
Процесс изменения коэффициентов (и положения прямой соответственно) показан на рисунке ниже:
Рассмотрим случай с тремя точками. Если они лежат на одной прямой, то будет существовать точка в пространстве параметров модели, в которой
Понятно, что у нас может быть не два параметра
Аналогично каждый объект может из себя представлять не одно значение
Тут также
На рисунке ниже показан пример подбора коэффициентов с помощью метода градиентного спуска для полинома второй степени.
Часто датасеты бывают очень большими, поэтому не всегда получается загрузить полный набор данных для обучения в компьютер. Поэтому придумали стохастический градиентный спуск.
Простыми словами это означает, что мы берем случайные выборки из исходной, считаем на них градиенты и потом усредняем. Это позволяет снизить требования к аппаратному обеспечению и повысить скорость вычислений в каждой итерации в обмен на снижение скорости сходимости к минимуму.
При этом, мне было не совсем понятно как именно выбрать размер выборок (batch size). Поэтому я решил подробнее изучить данный момент в этом репозитории.
Проект содержит в себе следующие файлы:
- В файле
data_gen.py
происходит генерация данных$X, Y$ . -
linear_model.py
показывает процесс градиентного спуска для задачи линейной регрессии. -
loss_surface.py
отрисовывает поверхность функции потерь для задачи с двумя точками. -
polynomial_model.py
показывает процесс градиентного спуска для полинома второй степени (при этом можно увеличить степень, но придется уменьшить значение$\lambda$ , иначе произойдет переполнение при подсчете градиента).
В процессе работы программы, в консоли выводятся также значения в формате [a0, a1]: loss
. Пример:
Вы можете найти меня здесь:
Также можете ознакомиться с моим резюме.