VIF란
- VIF는 다중 회귀 분석에서 다중공선성(Multicollinearity)을 진단하는 데 사용
- 다중공선성이란 독립 변수들 간에 높은 상관관계가 있을 때 발생하는 문제로, 회귀 분석 결과의 신뢰성을 떨어뜨릴 수 있다
- VIF는 각 독립 변수가 다른 독립 변수들에 의해 얼마나 설명되는지를 나타내며, 일반적으로 VIF 값이 10 이상이면 다중공선성 문제가 있다고 판단
파이썬 계산 방법
- 필요한 라이브러리 설치 및 불러오기
- variance_inflation_factor: VIF를 계산하는 함수.
- add_constant: 상수항(절편)을 추가하는 함수.
import pandas as pd
from statsmodels.stats.outliers_influence import variance_inflation_factor
from statsmodels.tools.tools import add_constant
- 데이터 준비
- 'x'라는 독립변수들로 이루어진 데이터프레임
# 예시 데이터 생성
np.random.seed(0)
X = pd.DataFrame({
'X1': np.random.rand(100),
'X2': np.random.rand(100),
'X3': np.random.rand(100)
})
- VIF 계산 함수 정의
def calculate_vif(data):
# 상수항 추가 (절편)
data_with_constant = add_constant(data)
# 각 변수에 대해 VIF 계산
vif = pd.DataFrame()
vif["Variable"] = data_with_constant.columns
vif["VIF"] = [variance_inflation_factor(data_with_constant.values, i) for i in range(data_with_constant.shape[1])]
return vif
- VIF 계산 및 출력
# VIF 계산
vif_result = calculate_vif(X)
print(vif_result)
Variable VIF
0 const 1.005021
1 X1 1.035414
2 X2 1.030454
3 X3 1.016608
VIF 값 해석:
VIF = 1: 해당 독립 변수와 다른 독립 변수 간에 상관관계가 없음을 의미합니다.
1 < VIF < 5: 일반적으로 허용 가능한 범위로 간주됩니다.
VIF ≥ 10: 다중공선성 문제가 있을 가능성이 높습니다.
해결 방법 1 - 상관관계가 높은 변수 제거
- VIF 값을 계산하여 다중공선성이 있는 변수를 식별
- VIF 값이 높은 변수를 제거
import pandas as pd
from statsmodels.stats.outliers_influence import variance_inflation_factor
from statsmodels.tools.tools import add_constant
# VIF 계산 함수
def calculate_vif(data):
data_with_constant = add_constant(data)
vif = pd.DataFrame()
vif["Variable"] = data_with_constant.columns
vif["VIF"] = [variance_inflation_factor(data_with_constant.values, i) for i in range(data_with_constant.shape[1])]
return vif
# 예시 데이터 생성
X = pd.DataFrame({
'X1': [1, 2, 3, 4, 5],
'X2': [2, 4, 6, 8, 10], # X1과 완벽한 상관관계
'X3': [5, 3, 4, 2, 1]
})
# VIF 계산 및 출력
vif_result = calculate_vif(X)
print(vif_result)
# X2와 X1이 매우 높은 상관관계를 보이면 X2를 제거
X_reduced = X.drop('X2', axis=1)
해결 방법 2 - 주성분분석(PCA)
- 주성분분석(Principal Component Analysis)은 상관된 변수를 비상관된 주성분으로 변환하여 다중공선성을 해결할 수 있는 방법
- 원래의 변수를 소수의 주성분으로 축소하여 사용
1. 필요한 라이브러리
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
from sklearn.decomposition import PCA
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression
from sklearn.metrics import mean_squared_error, r2_score
2. 예시 데이터 생성
# 예시 데이터 생성 (TV, Radio, Newspaper 광고비와 Sales)
data = {
'TV': np.random.rand(100) * 100,
'Radio': np.random.rand(100) * 50,
'Newspaper': np.random.rand(100) * 30,
'Sales': np.random.rand(100) * 100
}
df = pd.DataFrame(data)
# 독립 변수(X)와 종속 변수(y) 설정
X = df[['TV', 'Radio', 'Newspaper']] # 독립 변수들
y = df['Sales'] # 종속 변수 (판매량)
3. 데이터 분할(훈련용/테스트용)
# 데이터를 훈련용과 테스트용으로 분할 (80% 훈련, 20% 테스트)
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)
4. 주성분분석(PCA) 적용
PCA를 적용하여 독립 변수들의 차원을 축소합니다. 여기서는 주성분을 2개로 설정하였습니다.
# PCA 객체 생성 (주성분을 두 개로 축소)
pca = PCA(n_components=2)
# 훈련 데이터에 PCA 적용 (차원 축소)
X_train_pca = pca.fit_transform(X_train)
# 테스트 데이터에도 동일한 변환 적용
X_test_pca = pca.transform(X_test)
# 주성분 설명력 확인 (각 주성분이 설명하는 분산 비율)
print("주성분 설명력:", pca.explained_variance_ratio_)
출력 예시:
주성분 설명력: [0.6978 0.2887]
첫 번째 주성분이 약 69.78%, 두 번째 주성분이 약 28.87%의 분산을 설명합니다.
5. 다중 회귀 분석 모델 학습
PCA로 변환된 데이터를 사용하여 다중 회귀 모델을 학습합니다.
# 다중 선형 회귀 모델 생성 및 훈련 (PCA 변환된 데이터를 사용)
model = LinearRegression()
model.fit(X_train_pca, y_train)
# 예측 수행 (테스트 데이터에 대해)
y_pred = model.predict(X_test_pca)
# 회귀 계수 및 절편 출력
print("회귀 계수:", model.coef_)
print("절편:", model.intercept_)
출력 예시:
회귀 계수: [0.1234 -0.5678]
절편: 50.1234
6. 모델 평가
# 모델 평가 (MSE와 R² 계산)
mse = mean_squared_error(y_test, y_pred)
r2 = r2_score(y_test, y_pred)
print("평균 제곱 오차(MSE):", mse)
print("결정 계수(R²):", r2)
출력 예시:
평균 제곱 오차(MSE): 892.1234
결정 계수(R²): -0.0123
7. 시각화
# PCA로 변환된 첫 번째 주성분과 두 번째 주성분에 대한 산점도 및 회귀선 시각화
plt.scatter(X_test_pca[:, 0], y_test, color='blue', label='Actual Sales')
plt.scatter(X_test_pca[:, 0], y_pred, color='red', label='Predicted Sales')
plt.plot(X_test_pca[:, 0], y_pred, color='red', linewidth=2)
plt.title('PCA + Linear Regression')
plt.xlabel('First Principal Component')
plt.ylabel('Sales')
plt.legend()
plt.show()
'[업무 지식] > Statistics' 카테고리의 다른 글
[다항회귀] 비선형 관계 회귀 (0) | 2024.11.12 |
---|---|
[회귀 - 범주형] 다중선형회귀에서의 범주형 변수 (0) | 2024.11.12 |
[선형회귀] Regression (0) | 2024.11.12 |
[다중검정] 유의성 검정 (0) | 2024.11.12 |
[t검정] 유의성 검정 (0) | 2024.11.12 |