ОБРАБОТКА НЕБАЛАНСИРОВАННЫХ НАБОРОВ ДАННЫХ В ML | К ИИ

Акт балансировки в наборах данных алгоритма машинного обучения

Методы смягчения последствий обучения классификаторов с несбалансированными наборами данных в Python

Что происходит, когда вы тренируете классификатор с несбалансированными данными?

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

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

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

Низкие приоритеты, высокие приоритеты

Наивный байесовский

Допустим, вы строите модель прогнозирования для обнаружения мошенничества. У вас есть набор данных с 10 000 строками и некоторыми столбцами функций, где каждая строка помечена 1 для мошеннических транзакций или 0 для действительных транзакций. Для простоты я остановлюсь на одной функции, X. Структура выглядит так:

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

Formula: Pr(C1|E)/Pr(C2|E)/ = Pr(E|C1)*Pr(C1) / Pr(E|C2)*P(C2)

Модель предсказывает, какая из сторон отношения выше.

Если априорная вероятность Класса 1 очень мала, а априорная вероятность Класса 2 очень высока, наивная байесовская модель часто не может предсказать Класс 1, даже если вероятность Класса 1 (при наличии доказательств) очень высока и вероятность 2-го класса очень низкая.

Если рассматривать мошенничество как класс 1, а не мошенничество как класс 2, расчет для строки, в которой отсутствует функция X, будет следующим:

Pr(E|C1) = 90/100 = .9
Pr(C1) = 100/10,000 = .01
Pr(E|C2) = 10/100 = .1
Pr(C2) = 9,900/10,000 = .99
.9 * .01 / .1 * .99 = .009/.099

Поскольку знаменатель выше, модель будет предсказывать класс 2. И это несмотря на то, что свидетельства говорят в пользу мошенничества. В 90 из 100 случаев мошенничества отсутствует функция X, поэтому эта транзакция соответствует профилю большинства известных мошенников.

При такой низкой априорной вероятности класса 1 результат алгоритма почти всегда будет в пользу класса 2, независимо от свидетельств. В этом случае вероятность должна быть больше 0,99, чтобы перевесить чашу весов.

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

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

Логистическая регрессия - это еще один алгоритм классификации, который выводит вероятности. Линия наилучшего соответствия наносится на данные в логарифмической шкале шансов, а затем ось Y преобразуется в вероятности, превращая линию в s-образную кривую. По мере уменьшения x и выравнивания кривой внизу вероятность приближается к нулю; по мере увеличения x и выравнивания кривой вверху вероятность приближается к 1.

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

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

Стратегия 1. Измените априори с помощью бутстрэппинга.

Вы можете изменить априорные значения класса, передискретив данные.

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

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

На изображении ниже показаны данные до и после SMOTE:

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

Вы можете использовать SMOTE в конвейере «imblearn» с классификатором, а затем подогнать конвейер под свои данные следующим образом:

from imblearn.pipeline import Pipeline
from imblearn.over_sampling import SMOTE
smote = SMOTE()
cls = LogisticRegression()
pipe = Pipeline([(‘smt’, smote), (‘cls’, cls)])
pipe.fit(X_train, y_train)

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

Стратегия 2: настроить функцию потерь

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

class_weight = {0: 1,1: 10}

Вот как это выглядит с различными комбинациями весов для потерь журнала (- (ylog (p) + (1 − y) log (1 − p)) при правильной классификации 1.

Значения 0,5 или больше по оси абсцисс являются предсказаниями 1 с низкой или высокой вероятностью. Значения ниже 0,5 по оси x являются предсказаниями от 0 (не для класса 1) с высокой или низкой вероятностью. Чем выше вероятность, присвоенная 1 (правильный класс), тем меньше потери журнала. Чем выше вероятность, которую модель присваивает 0 (неправильный класс), тем выше потери журнала. Чем выше веса классов, которые мы присваиваем, тем выше штрафы за неверные прогнозы.

Стратегия 3. Измените порог прогноза

Если ваша модель предсказывает вероятность вашего класса меньшинства, так что вероятные случаи постоянно «скрываются от радаров» на уровне 30 или 40%, вы можете снизить порог для положительного прогноза.

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

probabilities = cls.predict_proba(x_test)[:,1]
y_hat = [1 if i>.35 else 0 for i in probabilities]

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

Подведение итогов

Вы можете справиться с несбалансированными классами следующим образом:

  • Смена априорной точки с ресэмплингом
  • Регулировка функции потерь
  • Изменение порога вероятности для предсказания

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

Ресурсы

Вот проект, который я сделал с Хелен Леви-Майерс и Адамом Бломфилдом, в котором используются некоторые из вышеперечисленных методов:



Вот несколько полезных ссылок: