Python(Colab) 의사 결정 나무(Decision Tree)
2023. 6. 13. 11:18ㆍ파이썬/머신러닝 및 딥러닝
✔ 의사 결정 나무
- 데이터를 분석하여 그 사이에 존재하는 패턴을 예측 가능한 규칙들의 조합으로 나타내며
그 모양이 나무와 유사하다하여 의사 결정 나무라고 부른다.
특징)
1. 분류와 회귀 모두 가능하다.
2. 지니계수(Gennie Index) : 0에 가까울수록 클래스에 속한 불순도가 낮다
3. 엔트로피(Entropy): 결정을 내릴만한 충분한 정보의 데이터가 없다고 보는 것
4. 과대적합(overfitting): 훈련데이터에서는 정확하나, 테스트 데이터에서는 성과가 나쁜 현상
훈련 데이터가 적거나, 노이즈가 있을 때 또는 알고리즘 자체가 나쁠때 발생
의사 결정 나무에서는 나무 가지가 많거나, 크기가 클 때 발생
cf) 과대 적합을 회피하기 위한 대책
1) 사전 가지치기: 나무가 다 자라기전에 알고리즘을 멈추는 법
2) 사후 가지치기: 의사 결정 나무를 다 돌린 후 밑에서부터 가지를 쳐나가는 작업
데이터로 실습
1. 기초 설정
import numpy as np
import pandas as pd
import seaborn as sns
import matplotlib.pyplot as plt
bike_df = pd.read_csv('/content/drive/MyDrive/KDT-1/머신러닝과 딥러닝/bike.csv')
데이터 설명
* datetime : 등록날짜
* count : 대여 개수
* holiday : 휴일 여부
* workingday : 평일 여부
* temp : 기온
* feels_like: 체감온도
* temp_min : 최저온도
* temp_max : 최고온도
* pressure : 기압
* humidity : 습도
* wind_speed : 풍속
* wind_deg : 풍향
* rain_1h : 강수량
* snow_1h : 강설량
* clouds_all : 구름의 양
* weather_main : 오늘 날씨
데이터 전처리
2. 이상치 확인
sns.boxplot(y=bike_df['count'])
3. 관련이 있어보이는 컬럼 찾기
후보1) feel_like= 체감온도
sns.scatterplot(x='feels_like',y='count',data=bike_df,alpha=0.3)
후보2) pressure = 기압
sns.scatterplot(x='pressure',y='count',data=bike_df,alpha=0.3)
후보3) wind_speed = 풍속
sns.scatterplot(x='wind_speed',y='count',data=bike_df,alpha=0.3)
후보4) wind_deg = 풍향
sns.scatterplot(x='wind_deg',y='count',data=bike_df,alpha=0.3)
4. 결측치 확인
rain_1h: 강수량 / snow_1h 강설량이 NaN이 있다
bike_df.isna().sum()
5. 결측치 처리
강수량 강설량의 NaN은 0으로 대체
bike_df = bike_df.fillna(0)
bike_df.isna().sum()
6. datetime 컬럼 타입 변경
object --> datetime으로
bike_df['datetime'] = pd.to_datetime(bike_df['datetime'])
bike_df.info()
7. datetime의 값 파생 변수로 분리하기
year, month, hour , date(ex)2018-01-01 4가지 파생변수 만들기
bike_df['year'] = bike_df['datetime'].dt.year
bike_df['month'] = bike_df['datetime'].dt.month
bike_df['hour'] = bike_df['datetime'].dt.hour
bike_df['date'] = bike_df['datetime'].dt.date
8.그래프로 시각화하여 확인
1) 날짜별 대여 개수 (date / count)
plt.figure(figsize=(14,4))
sns.lineplot(x='date',y='count',data=bike_df)
plt.xticks(rotation=45)
plt.show()
🔴그래프의 이상함을 파악 (2020/01~07)사이에 데이터가 이상하다
9. 2020년도 데이터 확인
bike_df[bike_df['year'] == 2020].groupby('month')['count'].mean()
2020년도 4월 데이터가 없다
결측치가 크고 예측하기 힘들기 때문에 다른 컬럼을 찾아보자
10. 코로나 기준으로 date를 바꾸기
2020-04-01 이전 : precovid
2021-04-01 이전 : covid
2021-04-01 이후 : postcovid
#방법 1
def covid(date):
if str(date) < '2020-04-01':
return 'precovid'
elif str(date) < '2021-04-01':
return 'covid'
else:
return 'postcovid'
bike_df['date'].apply(covid)
#방법 2
bike_df['covid'] = bike_df['date'].apply(lambda date: 'precovid' if str(date) < '2020-04-01'
else 'covid' if str(date) <'2021-04-01' else 'postcovid')
11. season이라는 파생 변수 만들기
3~5월 spring
6~8월 summer
9~11월 fall
12~2월 winter
bike_df['season'] = bike_df['month'].apply(lambda x: 'winter' if x == 12 else 'fall' if x >= 9 else 'summer' if x >= 6 else 'spring' if x >= 3 else 'winter')
#확인
bike_df[['month','season']]
12. day_night 파생 변수 만들기
bike_df['day_night'] = bike_df['hour'].apply(lambda x: 'night' if x >= 21
else 'late evening' if x >= 19
else 'early evening' if x >= 17
else 'late afternoon' if x >= 16
else 'early afternoon' if x >= 13
else 'late morning' if x >= 11
else 'early morning' if x >= 5
else 'night')
13. 머신러닝에 독립변수로 사용할 데이터타입 변경
#컬럼 별 개수 확인
for i in ['weather_main','covid','season','day_night']:
print(i,bike_df[i].nunique())
#원 핫 인코딩
bike_df = pd.get_dummies(bike_df,['weather_main','covid','season','day_night'])
원 핫 인코딩을 진행하기전에 데이터의 분류의 개수를 파악하는 것이 좋다.
14. 학습 데이터 + 검증 데이터 분리하기
from sklearn.model_selection import train_test_split
X_train, X_test, y_train, y_test = train_test_split(bike_df.drop('count',axis=1),bike_df['count'],test_size=0.2,random_state=10)
15. 의사결정 나무 사용해서 학습 시키기
from sklearn.tree import DecisionTreeRegressor
#하이퍼 파라미터로 random_state 미리 적용
dt = DecisionTreeRegressor(random_state=10)
#학습데이터 학습
dt.fit(X_train,y_train)
#검증데이터 테스트
pred1 = dt.predict(X_test)
16. 결과 검증
오차율 확인 (기준 : RMSE)
from sklearn.metrics import mean_squared_error
mean_squared_error(y_test,pred1,squared=False)
17. 선형 회귀랑 비교하기
from sklearn.linear_model import LinearRegression
lr = LinearRegression()
lr.fit(X_train,y_train)
pred2 = lr.predict(X_test)
mean_squared_error(y_test,pred2,squared=False)
18. 비교
# 의사결정나무 rmse 오차율 :228.42843328100884
# 선형회귀 rmse 오차율 :228.26128192004947
19. 의사결정나무에 하이퍼 파라미터 적용
dt = DecisionTreeRegressor(random_state=10, max_depth=50, min_samples_leaf=30)
✔ 하이퍼 파라미터
random_state: 학습,검증데이터가 변하지 않게 고정
max_depth: 데이터를 최대 50번 분리한다
min_samples_leaf = 남은 데이터가 30개 일시 알고리즘 종료
19.Tree 그래프로 확인
from sklearn.tree import plot_tree
plt.figure(figsize=(24,12))
plot_tree(dt,max_depth=5, fontsize=12, feature_names=X_train.columns)
plt.show()
max_depth: 최대 층을 설정해주는 것
feature_names: 어떤 컬럼의 데이터가 영향력이 있는지 표시
728x90
'파이썬 > 머신러닝 및 딥러닝' 카테고리의 다른 글
Python(Colab) 서포트 백터 머신 (Support Vector Machine) (0) | 2023.06.15 |
---|---|
Python(Colab) 로지스틱 회귀(Logistic Regression) (0) | 2023.06.14 |
Python(Colab) 선형 회귀(Linear Regression) (0) | 2023.06.12 |
Python(Colab) 타이타닉 데이터 셋 (Titanic data set)(LabelEncoder) (0) | 2023.06.12 |
Python(Colab) 아이리스 데이터 셋 (Iris data set)(Scikit-Learn) (0) | 2023.06.12 |