project:eve
23.01.27 Lasso, Elasticnet 라쏘, 엘라스틱넷 본문
오늘은 저번 릿지 회귀에 이어서 라쏘와 엘라스틱넷을 공부한다
*) 다중회귀 : 독립변수가 여러 개인 데이터셋을 대상으로 회귀
1. Lasso Regression

릿지 회귀는 모든 변수를 포함하고 변수의 계수(가중치)를 0에 가깝게 하는 것을 목적으로 한다. 즉 0으로 만들지는 않는다
그런데 이런 경우가 있다. 변수의 개수가 엄청나게 많아서 릿지 회귀로 0에 가깝게 만들더라도 값이 너무나 크게 나오는 경우에는? 변수 자체를 줄이지 않고는 해결될 수가 없다.
이럴때 라쏘 회귀를 사용한다. 라쏘 회귀는 릿지 회귀와 마찬가지로 변수의 계수를 0에 가깝게 만들 수 있고 더해서 일부 계수는 0으로 만들 수 있다. 계수가 0이 되는 변수들은 덜 중요한 특성이라고 할 수 있다. 즉 라쏘 회귀는 회소 모델을 만들 수 있다
(⚠️회소 모델?? 데이터의 차원/공간에 비해 데이터가 차지하는 공간은 협소한 모델링 기법이라고 생각하면 될 것 같다)
import pandas as pd
import numpy as np
from sklearn.datasets import load_diabetes
from sklearn.linear_model import Lasso
diab = load_diabetes()
df_diab = pd.DataFrame(diab.data, columns=diab.feature_names)
df_diab['result'] = diab.target
x = df_diab.drop(columns=['result'])
y = df_diab['result']
alpha = np.logspace(-3, 1, 5)
data = []
for i, a in enumerate(alpha):
lasso=Lasso(alpha=a)
lasso.fit(x, y)
data.append(lasso.coef_)
df_coef = pd.DataFrame(data, index=alpha)
df_coef.columns = x.columns
df_coef

릿지를 쓸 때와 마찬가지로 alpha값에 따른 독립변수의 가중치 값 변화를 데이터프레임으로 만들었다. 릿지와 다른 점이 있다면 alpha값이 제일 높을 때는 변수들의 가중치가 0이 된다는 것이다.
이렇게 구한 결정계수 값을 그래프로 표현해보자. alpha값에 따른 가중치들의 값 변화가 어떻게 0으로 변하는지 알 수 있다.
import matplotlib.pyplot as plt
fig = plt.figure()
plt.semilogx(df_coef)
plt.axhline(y=0, linestyle='--', linewidth=3)
plt.legend(df_coef.columns, bbox_to_anchor=(1,1))

단순선형회귀의 결정계수와 비교해 보자. 비교하기 쉽게 alpha값이 제일 작은 값과 제일 큰 값을 같이 그래프에 그린다.
from sklearn.linear_model import LinearRegression
Lr = LinearRegression()
Lr.fit(x, y)
fig = plt.figure()
plt.plot(df_coef.loc[0.001], 'r-', label='Lasso 0.001')
plt.plot(df_coef.loc[10], 'b-', label='Lasso 10')
plt.plot(Lr.coef_, '--', label='LinearRegression')
plt.legend(bbox_to_anchor=(1,1))

alpha값이 10인 선은 0과 동일한데 비해 alpha값이 제일 작은 선은 선형회귀 선과 똑같다.
2. Elasticnet

엘라스틱넷은 단순히 릿지와 라쏘 패널티를 더한 값이다. 주요 속성은 a 이외에 혼합비율인 r을 사용하는데, r=0이면 릿지 회귀, r=1이면 라쏘 회귀 추정치와 같다. 비율을 적절하게 지정해서 사용하는 것이 중요할 것 같다.
코드는 릿지, 라쏘와 대부분 비슷하기 때문에 간단하게 넘어가겠다
from sklearn.linear_model import ElasticNet
alpha = np.logspace(-3, 1, 5)
data = []
for i, a in enumerate(alpha):
ela = ElasticNet(alpha=a, l1_ratio=0.1)
ela.fit(x, y)
data.append(ela.coef_)
df_coef = pd.DataFrame(data, index=alpha)
df_coef.columns = x.columns
df_coef

l1_ratio 속성이 릿지-라쏘 혼합비율이고 높아질수록 라쏘 패널티의 값이 커진다. 처음에는 0.5로 했는데 alpha=10일 때 가중치가 모두 0이 나오길래 줄이다 보니 0.1까지 줄였다. 0.2부터는 대부분 0이다.
독립변수별로 alpha값에 따른 차이 알아보기
import matplotlib.pyplot as plt
fig=plt.figure()
plt.semilogx(df_coef)
plt.legend(df_coef.columns, bbox_to_anchor=(1,1))
plt.axhline(y=0, linestyle='--', linewidth=3)

선형회귀 선과 비교해보기. alpha값이 최소인데도 격차가 엄청나다.

'Daily' 카테고리의 다른 글
| 23.01.28 SVM 서포트 벡터 머신 (0) | 2023.01.29 |
|---|---|
| 23.01.28 Logistic Regression로지스틱 회귀 (0) | 2023.01.29 |
| 23.01.25 Linear Regression, Ridge 경사하강법, 릿지 회귀 (0) | 2023.01.25 |
| 23.01.24 Classification 분류분석 (0) | 2023.01.24 |
| 23.01.18 Regression 회귀분석 (0) | 2023.01.18 |