Kaggle 에서 notebook들을 보다보면 학습 데이터를 만들때 범주형 데이터를 사용하는 방법이 다 다릅니다.

One-Hot encoding을 주로 사용했는데 이번에 시계열 데이터를 다루면서 날짜별로 One-Hot encoding을 진행하면 Feature 의 수가 너무너무 많아져 이 부분에 대해 관심가지게 됐습니다.

그래서

  • 변주형 변수를 아무 처리 하지않고 그냥 사용
  • 변주형 변수를 category 타입으로 변경해 사용
  • 변주형 변수를 One-Hot encoding 한 후 사용

이 3가지 방법이 모델에 미치는 영향을 테스트 해봅시다.


데이터 준비

  • 테스트에 사용할 데이터는 Kaggle 에 있는 Titanic을 사용합니다.

  • 이전 포스팅 에서 Titanic 전처리를 다뤘기 때문에 전처리 과정은 생략합니다.

  • 범주형 변수는 Pclass, Sex, Embarked, Title 을 사용합니다.

1. 아무 처리를 하지 않은 데이터 셋 (normal_train)

 normal_train.info()
 -------------------------------------
 0   Pclass      891 non-null    int64
 1   Sex         891 non-null    int32
 2   Age         891 non-null    int32
 3   SibSp       891 non-null    int64
 4   Parch       891 non-null    int64
 5   Fare        891 non-null    int32
 6   Embarked    891 non-null    int32
 7   Title       891 non-null    int32
 8   Familysize  891 non-null    int64

2. category 탑으로 변경 (cg_train)

 cg_train.info()
 -------------------------------------
 0   Pclass      891 non-null    category
 1   Sex         891 non-null    category
 2   Age         891 non-null    int32   
 3   SibSp       891 non-null    int64   
 4   Parch       891 non-null    int64   
 5   Fare        891 non-null    int32   
 6   Embarked    891 non-null    category
 7   Title       891 non-null    category
 8   Familysize  891 non-null    int64 

3. One-Hot encoding (oh_train)

 oh_train.info()
 -------------------------------------
 0   Age         891 non-null    int32
 1   SibSp       891 non-null    int64
 2   Parch       891 non-null    int64
 3   Fare        891 non-null    int32
 4   Familysize  891 non-null    int64
 5   Pclass_1    891 non-null    uint8
 6   Pclass_2    891 non-null    uint8
 7   Pclass_3    891 non-null    uint8
 8   Sex_0       891 non-null    uint8
 9   Sex_1       891 non-null    uint8
 10  Embarked_0  891 non-null    uint8
 11  Embarked_1  891 non-null    uint8
 12  Embarked_2  891 non-null    uint8
 13  Title_0     891 non-null    uint8
 14  Title_1     891 non-null    uint8
 15  Title_2     891 non-null    uint8
 16  Title_3     891 non-null    uint8
 17  Title_4     891 non-null    uint8


K-Fold 교차검증(Random Forest)

  • 모델은 Random Forest의 default 값을 사용합니다.
  • K-Fold 교차 검증을 통해 정확도를 측정해 비교합니다.

1. 아무 처리를 하지 않은 데이터 셋 (normal_train)

In

model = RandomForestClassifier()
score1 = cross_val_score(model, normal_train, target, cv=kfold, scoring='accuracy')
mean1 = score1.mean()
print(f'normal train 의 정확도는 {mean1 * 100 :.2f}% 입니다.')

Out

normal train 의 정확도는 80.26% 입니다.

2. category 탑으로 변경 (cg_train)

In

model = RandomForestClassifier()
score2 = cross_val_score(model, cg_train, target, cv=kfold, scoring='accuracy')
mean2 = score2.mean()
print(f'category train 의 정확도는 {mean2 * 100 :.2f}% 입니다.')

Out

category train 의 정확도는 80.71% 입니다.

3. One-Hot encoding (oh_train)

In

model = RandomForestClassifier()
score3 = cross_val_score(model,oh_train, target, cv=kfold, scoring='accuracy')
mean3 = score3.mean()
print(f'one-hot encoding train 의 정확도는 {mean3 * 100 :.2f}% 입니다.')

Out

one-hot encoding train 의 정확도는 80.37% 입니다.

  • 정확도가 차이나 보이지만 판단을 하기가 애매합니다.
  • 실행할 때 마다 값이 달라지기 때문..
  • 혹시 모르니까 모델을 바꿔서 진행해봅니다.


K-Fold 교차검증(Support VectorClassification)

  • SVC (Support Vector Calssification) 을 이용해 테스트 해봅니다.

1. 아무 처리를 하지 않은 데이터 셋 (normal_train)

In

model = SVC()
score1 = cross_val_score(model, normal_train, target, cv=kfold, scoring='accuracy')
mean1 = score1.mean()
print(f'normal train 의 정확도는 {mean1 * 100 :.2f}% 입니다.')

Out

normal train 의 정확도는 82.50% 입니다.

2. category 탑으로 변경 (cg_train)

In

model = SVC()
score2 = cross_val_score(model, cg_train, target, cv=kfold, scoring='accuracy')
mean2 = score2.mean()
print(f'category train 의 정확도는 {mean2 * 100 :.2f}% 입니다.')

Out

category train 의 정확도는 82.50% 입니다.

3. One-Hot encoding (oh_train)

In

model = SVC()
score3 = cross_val_score(model,oh_train, target, cv=kfold, scoring='accuracy')
mean3 = score3.mean()
print(f'one-hot encoding train 의 정확도는 {mean3 * 100 :.2f}% 입니다.')

Out

one-hot encoding train 의 정확도는 83.40% 입니다.

  • SVC 에서는 One-Hot encoding 을 진행한 데이터셋이 약간더 높은 정확도를 보였습니다.
  • category 타입은 효과를 보지 못했습니다.


결과

  • 범주형 변수를 int 로 사용하나 category 로 사용하나 One-Hot encoding을 사용하나 Score에는 큰 영향을 주지 못했습니다.

  • 그래도 SVC 모델에서는 근소한 차이를 보였습니다.

  • 괜히 있는 기능이 아닐텐데 뭔가 이상합니다.

  • 생각해 볼 수 있는 점은

    1. 데이터의 양이 적다.
    2. Feature 의 영향이 크지 않다.
    3. Feature 의 개수가 변화를 줄 정도로 크지않다.
    4. 모델마다 영향을 받는 정도는 다르다.
  • 결론 : One-Hot encoding 은 아주 약간의 성능 향상을 기대 해 볼 수 있는 것 같습니다. category 타입은 의미 없는것 같습니다. 전체적으로 큰 성능향상은 모르겠습니다.


뭔가 뻘짓을 한 것 같지만 궁금증은 어느정도 해소됐습니다. 이 부분은 추가로 알게된 사실이 있다면 내용추가를 할 예정입니다.