본문으로 건너뛰기

010 setup() 전처리 옵션 - 스케일링

키워드: 스케일링, 정규화

개요

수치형 특성들은 서로 다른 범위와 단위를 가집니다. 예를 들어 나이는 0100 범위지만, 소득은 0수억 원 범위입니다. 이런 차이는 일부 알고리즘의 성능에 영향을 미칩니다. **스케일링(Scaling)**은 특성들의 범위를 맞춰주는 전처리 기법입니다. 이 글에서는 PyCaret의 스케일링 옵션을 알아보겠습니다.

실습 환경

  • Python 버전: 3.11 권장
    • Python 3.11은 2027년 말까지 지원되며, PyCaret 호환 최신 버전입니다.
  • 필요 패키지: pycaret[full]>=3.0, pandas, matplotlib
pip install pycaret[full]>=3.0 pandas matplotlib

Google Colab 사용 불가 Google Colab은 2025년 8월부터 Python 3.12만 지원하여 PyCaret(3.8~3.11) 실습이 불가능합니다. 로컬 환경이나 Docker를 사용해 주세요.

스케일링이 필요한 이유

스케일링 미적용 시 문제

from pycaret.datasets import get_data
import pandas as pd

data = get_data('insurance')
print(data[['age', 'bmi', 'charges']].describe())

출력:

              age         bmi       charges
count 1338.0000 1338.0000 1338.000000
mean 39.2070 30.6634 13270.422265
std 14.0500 6.0981 12110.011237
min 18.0000 15.9600 1121.873900
max 64.0000 53.1300 63770.428010
  • age: 18 ~ 64 범위
  • bmi: 15.96 ~ 53.13 범위
  • charges: 1,121 ~ 63,770 범위

이 상태로 KNN, SVM, 신경망을 학습하면 charges가 거리 계산을 지배합니다.

스케일링이 중요한 알고리즘

알고리즘스케일링 필요이유
KNN✅ 필수거리 기반
SVM✅ 필수거리 기반
신경망 (MLP)✅ 필수경사하강법
로지스틱 회귀⚠️ 권장수렴 속도
Ridge/Lasso⚠️ 권장정규화 영향
결정 트리❌ 불필요분할 기반
랜덤 포레스트❌ 불필요트리 앙상블
XGBoost/LightGBM❌ 불필요트리 기반

PyCaret 스케일링 옵션

normalize 파라미터

from pycaret.regression import *

clf = setup(
data=data,
target='charges',
normalize=True, # 스케일링 활성화
normalize_method='zscore', # 스케일링 방법
session_id=42
)

스케일링 방법 비교

방법파라미터수식범위
Z-score (표준화)'zscore'(x - mean) / std대부분 -3 ~ 3
Min-Max'minmax'(x - min) / (max - min)0 ~ 1
Max Absolute'maxabs'x / max(abs(x))-1 ~ 1
Robust'robust'(x - median) / IQR이상치에 강건

스케일링 방법 상세

1. Z-score 표준화 (기본값)

평균 0, 표준편차 1로 변환

clf = setup(
data=data,
target='charges',
normalize=True,
normalize_method='zscore',
session_id=42
)

변환 공식:

z = (x - μ) / σ

적합한 경우:

  • 정규분포에 가까운 데이터
  • 대부분의 경우 권장

2. Min-Max 스케일링

0~1 범위로 변환

clf = setup(
data=data,
target='charges',
normalize=True,
normalize_method='minmax',
session_id=42
)

변환 공식:

x_scaled = (x - x_min) / (x_max - x_min)

적합한 경우:

  • 특정 범위가 필요할 때
  • 신경망 입력
  • 이미지 데이터

3. Max Absolute 스케일링

최대 절대값으로 나눔

clf = setup(
data=data,
target='charges',
normalize=True,
normalize_method='maxabs',
session_id=42
)

적합한 경우:

  • 희소 행렬 (0이 많은 데이터)
  • 0을 유지해야 할 때

4. Robust 스케일링

중앙값과 IQR 사용 (이상치에 강건)

clf = setup(
data=data,
target='charges',
normalize=True,
normalize_method='robust',
session_id=42
)

변환 공식:

x_scaled = (x - median) / IQR
IQR = Q3 - Q1 (사분위수 범위)

적합한 경우:

  • 이상치가 많은 데이터
  • 비대칭 분포

실전 예제: 스케일링 효과 비교

from pycaret.regression import *
from pycaret.datasets import get_data

data = get_data('insurance')

# 010 스케일링 없이
print("=" * 50)
print("스케일링 없음")
print("=" * 50)
reg1 = setup(
data=data,
target='charges',
normalize=False,
session_id=42,
verbose=False
)
# 010 SVM 모델 (스케일링 민감)
svm1 = create_model('svm', verbose=False)
results1 = pull()
print(f"SVM R2: {results1['R2'].mean():.4f}")

# 010 Z-score 스케일링
print("\n" + "=" * 50)
print("Z-score 스케일링")
print("=" * 50)
reg2 = setup(
data=data,
target='charges',
normalize=True,
normalize_method='zscore',
session_id=42,
verbose=False
)
svm2 = create_model('svm', verbose=False)
results2 = pull()
print(f"SVM R2: {results2['R2'].mean():.4f}")

# 010 Min-Max 스케일링
print("\n" + "=" * 50)
print("Min-Max 스케일링")
print("=" * 50)
reg3 = setup(
data=data,
target='charges',
normalize=True,
normalize_method='minmax',
session_id=42,
verbose=False
)
svm3 = create_model('svm', verbose=False)
results3 = pull()
print(f"SVM R2: {results3['R2'].mean():.4f}")

출력 예시:

==================================================
스케일링 없음
==================================================
SVM R2: -0.0821

==================================================
Z-score 스케일링
==================================================
SVM R2: 0.7423

==================================================
Min-Max 스케일링
==================================================
SVM R2: 0.7156

스케일링 없이는 SVM이 전혀 학습하지 못하지만, 스케일링 후 성능이 크게 향상됩니다!

트리 기반 모델에서의 스케일링

트리 기반 모델은 스케일링이 불필요합니다:

from pycaret.regression import *
from pycaret.datasets import get_data

data = get_data('insurance')

# 010 스케일링 없이
reg1 = setup(data, target='charges', normalize=False, session_id=42, verbose=False)
rf1 = create_model('rf', verbose=False)
results1 = pull()
print(f"RF (스케일링 X): R2 = {results1['R2'].mean():.4f}")

# 010 스케일링 적용
reg2 = setup(data, target='charges', normalize=True, session_id=42, verbose=False)
rf2 = create_model('rf', verbose=False)
results2 = pull()
print(f"RF (스케일링 O): R2 = {results2['R2'].mean():.4f}")

출력:

RF (스케일링 X): R2 = 0.8521
RF (스케일링 O): R2 = 0.8519

랜덤 포레스트는 스케일링 여부에 거의 영향받지 않습니다.

스케일링 시각화

import matplotlib.pyplot as plt
import numpy as np
from sklearn.preprocessing import StandardScaler, MinMaxScaler, RobustScaler

# 010 샘플 데이터
np.random.seed(42)
data_sample = np.concatenate([
np.random.normal(50, 10, 100),
np.array([150, 200]) # 이상치
])

# 010 스케일링
scalers = {
'Original': data_sample,
'Z-score': StandardScaler().fit_transform(data_sample.reshape(-1, 1)).flatten(),
'Min-Max': MinMaxScaler().fit_transform(data_sample.reshape(-1, 1)).flatten(),
'Robust': RobustScaler().fit_transform(data_sample.reshape(-1, 1)).flatten()
}

# 010 시각화
fig, axes = plt.subplots(2, 2, figsize=(12, 8))
axes = axes.flatten()

for ax, (name, values) in zip(axes, scalers.items()):
ax.hist(values, bins=20, edgecolor='black', alpha=0.7)
ax.set_title(f'{name}')
ax.set_xlabel('Value')
ax.set_ylabel('Frequency')

plt.tight_layout()
plt.savefig('scaling_comparison.png')

스케일링 선택 가이드

상황권장 스케일링
일반적인 경우Z-score ('zscore')
신경망 입력Min-Max ('minmax')
이상치가 많음Robust ('robust')
희소 데이터Max Absolute ('maxabs')
트리 기반 모델만 사용불필요 (normalize=False)

타겟 변수 변환

회귀 문제에서 타겟 변수도 변환할 수 있습니다:

clf = setup(
data=data,
target='charges',
transform_target=True, # 타겟 변환 활성화
transform_target_method='yeo-johnson', # 변환 방법
session_id=42
)

타겟 변환 방법:

  • 'yeo-johnson': 음수 포함 가능
  • 'box-cox': 양수만 가능
  • 'quantile': 균등 분포로 변환

적합한 경우:

  • 타겟이 비대칭 분포일 때
  • 타겟에 이상치가 있을 때

정리

  • 스케일링은 특성들의 범위를 맞춰주는 전처리입니다.
  • KNN, SVM, 신경망 등 거리 기반 알고리즘에는 필수입니다.
  • 트리 기반 모델(RF, XGBoost 등)에는 불필요합니다.
  • normalize=True로 활성화하고, normalize_method로 방법을 선택합니다.
  • 이상치가 많으면 'robust' 스케일링을 사용하세요.
  • PyCaret의 compare_models()는 여러 알고리즘을 테스트하므로 스케일링을 적용하는 것이 좋습니다.

다음 글 예고

다음 글에서는 setup() 전처리 옵션 - 특성 선택에 대해 알아보겠습니다. 불필요한 특성을 제거하고 중요한 특성만 선택하여 모델 성능을 향상시키는 방법을 다룹니다.


PyCaret 머신러닝 마스터 시리즈 #010