머신러닝·딥러닝 문제해결 전략 책을 읽으면서
Kaggle 경진대회 코드와 문제해결 전략을 정리한 글
베이스라인 모델 전체 프로세스
1. 데이터 불러오기
2. (기본적인) 피처 엔지니어링 → 모든 피처 원-핫 인코딩
3. 평가지표 계산 함수 작성 → ROC AUC 사용 (사이킷런 제공)
4. 모델 훈련 → 로지스틱 회귀 (사이킷런 제공)
5. 성능 검증
6. 제출
# 훈련, 테스트, 제출 샘플 파일 불러오기
import pandas as pd
data_path = '/kaggle/input/cat-in-the-dat/'
train = pd.read_csv(data_path + 'train.csv', index_col='id')
test = pd.read_csv(data_path + 'test.csv', index_col='id')
submission = pd.read_csv(data_path + 'sample_submission.csv', index_col='id')
인코딩
이라고 함all_data = pd.concat([train, test]) # 훈련 데이터와 테스트 데이터 합치기
all_data = all_data.drop('target', axis=1) # 타깃값 제거
all_data
bin_0 | bin_1 | bin_2 | bin_3 | bin_4 | nom_0 | ... | nom_9 | ord_0 | ord_1 | ord_2 | ord_3 | ord_4 | ord_5 | day | month | |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
id | ||||||||||||||||
0 | 0 | 0 | 0 | T | Y | Green | ... | 2f4cb3d51 | 2 | Grandmaster | Cold | h | D | kr | 2 | 2 |
1 | 0 | 1 | 0 | T | Y | Green | ... | f83c56c21 | 1 | Grandmaster | Hot | a | A | bF | 7 | 8 |
2 | 0 | 0 | 0 | F | Y | Blue | ... | ae6800dd0 | 1 | Expert | Lava Hot | h | R | Jc | 7 | 2 |
3 | 0 | 1 | 0 | F | Y | Red | ... | 8270f0d71 | 1 | Grandmaster | Boiling Hot | i | D | kW | 2 | 1 |
4 | 0 | 0 | 0 | F | N | Red | ... | b164b72a7 | 1 | Grandmaster | Freezing | a | R | qP | 7 | 8 |
... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... | ... |
499995 | 0 | 0 | 0 | F | N | Green | ... | acc31291f | 1 | Novice | Lava Hot | j | A | Gb | 1 | 3 |
499996 | 1 | 0 | 0 | F | Y | Green | ... | eae3446d0 | 1 | Contributor | Lava Hot | f | S | Ed | 2 | 2 |
499997 | 0 | 1 | 1 | T | Y | Green | ... | 33dd3cf4b | 1 | Novice | Boiling Hot | g | V | TR | 3 | 1 |
499998 | 1 | 0 | 0 | T | Y | Blue | ... | d4cf587dd | 2 | Grandmaster | Boiling Hot | g | X | Ye | 2 | 1 |
499999 | 0 | 0 | 0 | T | Y | Green | ... | 2d610f52c | 2 | Novice | Freezing | l | J | ex | 2 | 2 |
500000 rows × 23 columns
훈련 데이터와 테스트 데이터를 합하면 행 개수가 50만 개이며, 타깃값이 빠져서 피처는 23개임
all_data
에는 문자로 구성된 피처와 숫자로 구성된 피처가 섞여 있음. 문자로 구성된 피처는 반드시 인코딩해야 하지만 숫자로 구성된 피처는 모델링하는 데 지장을 주지 않아서 반드시 인코딩할 필요는 없음. 단, 모델 성능을 더 좋게 하려고 숫자로 구성된 범주형 피처도 인코딩하는 경우가 있음. 여기서는 편의상 모든 피처를 인코딩하고 모델 성능을 개선할 때 피처 특성에 따라 다른 인코딩을 적용할 것
from sklearn.preprocessing import OneHotEncoder
encoder = OneHotEncoder() # 원-핫 인코더 생성
all_data_encoded = encoder.fit_transform(all_data) # 원-핫 인코딩 적용
num_train = len(train) # 훈련 데이터 개수
# 훈련 데이터와 테스트 데이터 나누기
X_train = all_data_encoded[:num_train] # 0 ~ num_train-1 행
X_test = all_data_encoded[num_train:] # num_train ~ 마지막 행
y = train['target'] # 타깃값 저장
훈련 데이터에서 일부를 검증 데이터로 나누어 훈련 데이터는 모델 훈련에 사용하고, 검증 데이터는 모델 성능 검증에 사용하도록 함
이렇게 하면 검증 데이터를 이용해 제출 전에 모델 성능을 평가해볼 수 있음
from sklearn.model_selection import train_test_split
# 훈련 데이터, 검증 데이터 분리
X_train, X_valid, y_train, y_valid = train_test_split(X_train, y,
test_size=0.1,
stratify=y,
random_state=10)
test_size
는 검증 데이터 크기를 지정하는 파라미터 stratify
는 지정한 값을 각 그룹에 '공정하게' 배분하는 파라미터 random_state
는 시드값을 고정하여 다음에 실행해도 같은 결과가 나오게 해줌from sklearn.linear_model import LogisticRegression
logistic_model = LogisticRegression(max_iter=1000, random_state=42) # 모델 생성
logistic_model.fit(X_train, y_train) # 모델 훈련
LogisticRegression(max_iter=1000, random_state=42)
베이스라인 모델이므로 모델의 파라미터는 간단하게 설정
predict()
: 타깃값 자체(0이냐 1이냐)를 예측 predict_proba()
: 타깃값의 확률(0일 확률과 1일 확률)을 예측# predict_proba()로 검증 데이터의 타깃값이 0 또는 1일 확률을 예측
logistic_model.predict_proba(X_valid)
array([[0.23262216, 0.76737784],
[0.91407764, 0.08592236],
[0.83025174, 0.16974826],
...,
[0.24875927, 0.75124073],
[0.49441807, 0.50558193],
[0.95661255, 0.04338745]])
# predict()로 타깃값을 0 또는 1로 예측
logistic_model.predict(X_valid)
array([1, 0, 0, ..., 1, 1, 0])
본 대회에서는 타깃값이 1일 '확률'을 예측해야 하므로 predict_proba()
메서드로 예측한 결과의 두 번째 열을 타깃 예측값으로 사용
# 검증 데이터를 활용한 타깃 예측
y_valid_preds = logistic_model.predict_proba(X_valid)[:, 1]
타깃 예측값인 y_valid_preds
와 실제 타깃값인 y_valid
를 이용해 ROC AUC 구하기
from sklearn.metrics import roc_auc_score # ROC AUC 점수 계산 함수
# 검증 데이터 ROC AUC
roc_auc = roc_auc_score(y_valid, y_valid_preds)
print(f'검증 데이터 ROC AUC : {roc_auc:.4f}')
검증 데이터 ROC AUC : 0.7965
# 타깃값이 1일 확률 예측
y_preds = logistic_model.predict_proba(X_test)[:, 1]
# 제출 파일 생성
submission['target'] = y_preds
submission.to_csv('submission.csv')