Machine Learning

레이블인코딩(Label Encoding) vs 원핫인코딩(One-hot Encoding) 비교

hyez 2022. 2. 28. 13:12

컴퓨터는 인간의 언어를 이해하지 못한다. 우리가 컴퓨터에 한글을 입력한다 해도 컴퓨터가 받아들이는 것은 0과 1의 이진수로 이해를 하게된다.

따라서 우리가 머신러닝/딥러닝을 할 때 문자열의 값들을 숫자형으로 인코딩하는 전처리 단계가 필요하다. 

인코딩 방식으로는 레이블 인코딩(Label encoding), 원-핫 인코딩(One-hot encoding) 두 가지 방식이 있다.

출처 : https://ichi.pro/ko/label-inkoding-gwa-won-has-inkoding-255778339871323

그렇다면 어떤 인코딩 방식을 써야할까?

 

Label Encoding

Label Encoding이란 문자열의 unique값을 숫자로 바꿔주는 방법이다.

from sklearn.preprocessing import LabelEncoder

fruit=['바나나', '사과', '사과', '포도', '딸기', '포도', '바나나']
print(sorted(set(fruit)))
encoder = LabelEncoder()
labels = encoder.fit_transform(fruit)
print(labels)

# outputs
# ['딸기', '바나나', '사과', '포도']
# [1 2 2 3 0 3 1]

fruit라는 변수를 내림차순으로 정렬하여 번호를 부여했다. 다만 데이터가 많을 경우에 해당 class에 대한 직관적인 인식이 어려울 때는, classes_ 속성 값을 사용할 수 있다.

print(encoder.classes_)
print(encoder.inverse_transform([0, 1, 2, 3]))

#['딸기' '바나나' '사과' '포도']
#['딸기' '바나나' '사과' '포도']

문제점

  • 숫자값으로 변환되어 숫자의 ordinal한 특성이 반영되기 독립적인 관측값간의 관계성이 생긴다.
  • 숫자값을 가중치로 잘못 인식하여 값에 왜곡이 생긴다
  • ex) 1+2 = 3, 1<2<3<4

이러한 특성은 예측 성능의 저하를 일으키고, 레이블 인코딩은 선형회귀와 같은 ML알고리즘에는 보통 적용하지 않는다. 하지만 트리계열의 ML알고리즘은 숫자의 ordinal 특성을 반영하지 않으므로 레이블 인코딩도 별 문제 없다.

 

One-Hot Encoding

One-Hot Encoding이란 long-type으로 구성된 변수들을 wide-type으로 목록화하여 변수의 차원을 늘린다. 이후 개별로 해당 컬럼이 맞으면 1 아니면 0의 이진수를 갖는다.

 

원-핫 인코딩은 sklearn의 OneHotEncoder 클래스로 쉽게 가능하나, 문자열에서 바로 변환은 되지 않기에, 라벨인코더를 통해 숫자로 변환 후 사용가능하다.

from sklearn.preprocessing import OneHotEncoder
import numpy as np

fruit=['바나나', '사과', '사과', '포도', '딸기', '포도', '바나나']

#Step1: 모든 문자를 숫자형으로 변환합니다.
encoder = LabelEncoder()
encoder.fit(fruit)
labels = encoder.transform(fruit)

#Step2: 2차원 데이터로 변환합니다.
labels = labels.reshape(-1, 1)

#Step3: One-Hot Encoding 적용합니다.
oh_encoder = OneHotEncoder()
oh_encoder.fit(labels)
oh_labels = oh_encoder.transform(labels)
print(oh_labels.toarray())
print(oh_labels.shape)

# [[0. 1. 0. 0.]
# [0. 0. 1. 0.]
# [0. 0. 1. 0.]
# [0. 0. 0. 1.]
# [1. 0. 0. 0.]
# [0. 0. 0. 1.]
# [0. 1. 0. 0.]]
# (7, 4)

Pandas의 get_dummies()

판다스에서는 get_dummies() 메서드를 사용하여 쉽게 변환이 가능하다.

import pandas as pd

fruit = ['바나나', '사과', '사과', '포도', '딸기', '포도', '바나나']
df = pd.DataFrame({'fruit':fruit})
pd.get_dummies(df)

문제점

Dummy Variable Trap은 One-Hot Encoding한 변수 하나의 결과가 다른 변수의 도움으로 쉽게 예측되어 질수 있다는 것이다. => 다중공선성

 

다중 공선성(multicollinearity)

독립변수들 간에 강한 상관관계가 나타나는 문제이다.

진단법

  1. 결정계수 R2값은 높아 회귀식의 설명력은 높지만 식안의 독립변수의 P값(P-value)이 커서 개별 인자들이 유의하지 않는 경우가 있다. 이런 경우 독립변수들 간에 높은 상관관계가 있다고 의심된다.
  2. 독립변수들간의 상관계수를 구한다.
  3. 분산팽창요인(Variance Inflation Factor,VIF)를 구하여 이 값이 10을 넘는다면 보통 다중공선성의 문제가 있다.
from statsmodels.stats.outliers_influence import variance_inflation_factor

해결법

  1. 상관관계가 높은 독립변수중 하나 혹은 일부를 제거한다.
  2. 변수를 변형시키거나 새로운 관측치를 이용한다.
  3. 자료를 수집하는 현장의 상황을 보아 상관관계의 이유를 파악하여 해결한다.
  4. 주성분 분석(PCA,Principle Component Analysis)를 이용한 diagonal matrix의 형태로 공선성을 없애준다.

 

Reference