Правильный способ меток классов с одним горячим кодированием для многоклассовой задачи - PullRequest
1 голос
/ 14 апреля 2020

У меня проблема классификации с несколькими классами, назовем их A, B, C и D. Мои данные имеют следующую форму:

X=[#samples, #features, 1], y=[#samples,1].

Чтобы быть более точным c, у выглядит так:

[['A'], ['B'], ['D'], ['A'], ['C'], ...]

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

[[1,0,0,0], [0,1,0,0], ...]

и имеет форму

[#samples, 4]

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

# [array([0, 1]), array([0, 1]), array([0, 1]), array([0, 1])]

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

Ответы [ 2 ]

1 голос
/ 14 апреля 2020

Ваш первоначальный подход, без горячего кодирования, выполнял то, что вы хотели.

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

Для выходных меток такой классификатор, как RandomForest, отлично подходит для строк и нескольких классов.

1 голос
/ 14 апреля 2020

Вам не нужно делать одну горячую кодировку при использовании случайного леса в sklearn.

Вам нужен «кодировщик меток», и ваш Y должен выглядеть как

from sklearn.preprocessing import LabelEncoder
y = ["A","B","D","A","C"]
le = LabelEncoder()
le.fit_transform(y)
# array([0, 1, 3, 0, 2], dtype=int64)

Я пытался изменить пример кода sklearn при условии :

from sklearn.ensemble import RandomForestClassifier
import numpy as np
from sklearn.datasets import make_classification

>>> X, y = make_classification(n_samples=1000, n_features=4,
...                            n_informative=2, n_redundant=0,
...                            random_state=0, shuffle=False)
y = np.random.choice(["A","B","C","D"],1000)
print(y.shape)
>>> clf = RandomForestClassifier(max_depth=2, random_state=0)
>>> clf.fit(X, y)
>>> clf.classes_
# array(['A', 'B', 'C', 'D'], dtype='<U1')

Либо обрабатывать y с кодировкой метки, либо без, обе они работали с RandomForestClassifier.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...