인간의 지능을 모방한 인공적인 지능
인간의 학습능력과 추론능력, 지각능력, 자연어의 이해능력 등을 컴퓨터 프로그램으로 실현한 기술
명시적으로 프로그래밍하지 않고도 컴퓨터에 학습할 수 있는 능력을 부여하는 것
컴퓨터가 데이터를 분석하고 스스로 학습하는 과정을 통해 인공적인 지능을 갖도록 하는 학습방법
열역학의 용어로 물질의 열적 상태를 나타내는 물리량
무질서도, 불확실성을 의미함
불순도율을 의미함
엔트로피와 동일하게 수치가 낮을수록 좋은 결과를 얻음
log를 사용하는 엔트로피와 다르게 지니계수는 단순 산술이므로 처리부하가 적음
from sklearn.tree import DecisionTreeClassifier
iris_tree = DecisionTreeClassifier()
feature = iris.data[:, 2:] # 학습데이터(petal만 사용)
target = iris.target # 정답 데이터
iris_tree.fit(feature, target)
# 학습 결과 확인
from sklearn.metrics import accuracy_score
y_pred_tr = iris_tree.predict(feature)
accuracy_score(iris.target, y_pred_tr)
---------------------------------------
0.9933333333333333
from sklearn.tree import plot_tree
plt.figure(figsize=(10,10))
plot_tree(iris_tree, filled=True)
plt.show()
from mlxtend.plotting import plot_decision_regions
import matplotlib
matplotlib.rcParams['axes.unicode_minus'] = False
plt.figure(figsize=(14,8))
plot_decision_regions(X=feature, y=target, clf=iris_tree, legend=2)
plt.title('결정 경계')
plt.show()
1,2번 사이의 경계선이 복잡하고, 위에서 정확도를 구했을 때, 99%가 나왔는데 이것은 과적합된 것이다.
주어진 학습데이터 150개에 대해서만 결과가 다음과 같이 나온 것이지, 이것이 모든 iris를 대표한다고 할 수 없기 때문이다.
->성급한 일반화의 오류 가능성
복잡한 경계면은 모델의 성능을 결국 나쁘게 만든다.
경계면에 복잡한 부근에 있는 데이터들이 이상치일 가능성은 없는것인가? 신뢰할 수 있는가?
일반적인 데이터를 기준으로 모델의 성능을 향상시키려면 어느 정도의 오류는 감수해야 한다.
from sklearn.datasets import load_iris
from sklearn.model_selection import train_test_split
import pandas as pd
iris = load_iris()
features = iris.data[:, 2:]
labels = iris.target
# 데이터분리
X_train, X_test, y_train, y_test = train_test_split(features, labels, test_size=0.2, stratify=labels, random_state=13)
# 분리 형태 확인
X_train.shape, X_test.shape
-----------------------------------------------------------------------------------------------------
((120, 2), (30, 2))
import numpy as np
np.unique(y_test, return_counts=True)
----------------------------------------------------
(array([0, 1, 2]), array([10, 10, 10], dtype=int64))
from sklearn.tree import DecisionTreeClassifier
from sklearn.tree import plot_tree
iris_tree = DecisionTreeClassifier(max_depth=2, random_state=13)
iris_tree.fit(X_train, y_train)
plt.figure(figsize=(7,7))
plot_tree(iris_tree, filled=True)
plt.show()
from sklearn.metrics import accuracy_score
y_pred_tr = iris_tree.predict(X_train)
accuracy_score(y_train, y_pred_tr)
-------------------------------------------
0.95
# 예측하기
test_data = [[4.3, 2., 1.2, 1.]]
iris_tree.predict(test_data)
----------------------------------
array([1])
iris.target_names[iris_tree.predict(test_data)]
-----------------------------------------------
array(['versicolor'], dtype='<U10')
문자를 숫자로, 숫자를 문자로 변환
머신러닝에 적용하기 위해서는 문자를 숫자로 변환 필요
학습이 끝난 후 얻은 결과를 숫자로 변환해서 확인 가능
df['le_A'] = le.transform(df['A'])
df
-------------------------------------------------
A B le_A
0 a 1 0
1 b 2 1
2 c 3 2
3 a 1 0
4 b 0 1
le.fit_transform(df['A'])
--------------------------
array([0, 1, 2, 0, 1])
le.inverse_transform(df['le_A'])
---------------------------------
array(['a', 'b', 'c', 'a', 'b'], dtype=object)
# 3개의 모델을 선언
from sklearn.preprocessing import MinMaxScaler, StandardScaler, RobustScaler
mm = MinMaxScaler()
ss = StandardScaler()
rs = RobustScaler()
# 하나의 데이터프레임에 저장
df_scaler = df.copy()
df_scaler['MinMax'] = mm.fit_transform(df)
df_scaler['Standard'] = ss.fit_transform(df)
df_scaler['Robust'] = rs.fit_transform(df)
df_scaler
--------------------------------------
A MinMax Standard Robust
0 -0.1 0.000000 -0.656688 -0.444444
1 0.0 0.019608 -0.590281 -0.333333
2 0.1 0.039216 -0.523875 -0.222222
3 0.2 0.058824 -0.457468 -0.111111
4 0.3 0.078431 -0.391061 0.000000
5 0.4 0.098039 -0.324655 0.111111
6 1.0 0.215686 0.073785 0.777778
7 1.1 0.235294 0.140192 0.888889
8 5.0 1.000000 2.730051 5.222222
import seaborn as sns
import matplotlib.pyplot as plt
sns.set_theme(style="whitegrid")
plt.figure(figsize=(16,6))
sns.boxplot(data=df_scaler, orient="h")
plt.show()
import pandas as pd
red_url = 'https://raw.githubusercontent.com/Pinkwink/ML_tutorial/master/dataset/winequality-red.csv'
white_url = 'https://raw.githubusercontent.com/Pinkwink/ML_tutorial/master/dataset/winequality-white.csv'
red_wine = pd.read_csv(red_url, sep=';')
white_wine = pd.read_csv(white_url, sep=';')
red_wine['color']=1.
white_wine['color']=0.
wine = pd.concat([red_wine, white_wine])
X = wine.drop(['color'], axis=1)
y = wine['color']
# 파이프라인 구성
from sklearn.pipeline import Pipeline
from sklearn.tree import DecisionTreeClassifier
from sklearn.preprocessing import StandardScaler
estimators = [
('scaler', StandardScaler()),
('clf', DecisionTreeClassifier())
]
pipe = Pipeline(estimators)
pipe.steps
-----------------------------------------------------------------
[('scaler', StandardScaler()), ('clf', DecisionTreeClassifier())]
pipe.set_params(clf__max_depth=2)
pipe.set_params(clf__random_state=13)
from sklearn.model_selection import train_test_split
from sklearn.metrics import accuracy_score
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=13, stratify=y)
pipe.fit(X_train, y_train)
y_pred_tr = pipe.predict(X_train)
y_pred_test = pipe.predict(X_test)
print('Train Acc : ', accuracy_score(y_train, y_pred_tr))
print('Test Acc : ', accuracy_score(y_test, y_pred_test))
---------------------------------------------------------
Train Acc : 0.9657494708485664
Test Acc : 0.9576923076923077
from sklearn.model_selection import KFold
from sklearn.tree import DecisionTreeClassifier
kfold = KFold(n_splits=5) # 분할 갯수 K 결정
wine_tree_cv = DecisionTreeClassifier(max_depth=2, random_state=13)
# StratifiedKFold
from sklearn.model_selection import StratifiedKFold
from sklearn.model_selection import cross_val_score
skfold = StratifiedKFold(n_splits=5) # 분할 갯수 K 결정
wine_tree_cv = DecisionTreeClassifier(max_depth=2, random_state=13)
cross_val_score(wine_tree_cv, X, y, scoring=None, cv=skfold)
--------------------------------------------------------------------
array([0.55230769, 0.68846154, 0.71439569, 0.73210162, 0.75673595])
하이퍼파라미터의 최적의 값을 도출
설정해놓은 값들을 반복해서 넣고 그 결과를 비교하는 방식을 사용하므로 시간이 오래걸린다.
from sklearn.model_selection import GridSearchCV
from sklearn.tree import DecisionTreeClassifier
params = {'max_depth' : [2,4,7,10]}
wine_tree = DecisionTreeClassifier(max_depth=2, random_state=13)
gridsearch = GridSearchCV(estimator=wine_tree, param_grid=params, cv=5, n_jobs=7) # cv는 분할갯수
gridsearch.fit(X,y)
import pprint
pp = pprint.PrettyPrinter(indent=4)
pp.pprint(gridsearch.cv_results_)
---------------------------------------------------------------------------------
{ 'mean_fit_time': array([0.01557207, 0.02707362, 0.03694801, 0.0396534 ]),
'mean_score_time': array([0.00433187, 0.00419917, 0.00400963, 0.00239401]),
'mean_test_score': array([0.6888005 , 0.66356523, 0.65340854, 0.64401587]),
'param_max_depth': masked_array(data=[2, 4, 7, 10],
mask=[False, False, False, False],
fill_value='?',
dtype=object),
'params': [ {'max_depth': 2},
{'max_depth': 4},
{'max_depth': 7},
{'max_depth': 10}],
'rank_test_score': array([1, 2, 3, 4]),
'split0_test_score': array([0.55230769, 0.51230769, 0.50846154, 0.51615385]),
'split1_test_score': array([0.68846154, 0.63153846, 0.60307692, 0.60076923]),
'split2_test_score': array([0.71439569, 0.72363356, 0.68360277, 0.66743649]),
'split3_test_score': array([0.73210162, 0.73210162, 0.73672055, 0.71054657]),
'split4_test_score': array([0.75673595, 0.7182448 , 0.73518091, 0.72517321]),
'std_fit_time': array([0.002706 , 0.00254519, 0.00184818, 0.00089921]),
'std_score_time': array([0.00041986, 0.00115462, 0.00166992, 0.00048907]),
'std_test_score': array([0.07179934, 0.08390453, 0.08727223, 0.07717557])}
from sklearn.pipeline import Pipeline
from sklearn.tree import DecisionTreeClassifier
from sklearn.preprocessing import StandardScaler
estimators = [
('scaler', StandardScaler()),
('clf', DecisionTreeClassifier())
]
pipe = Pipeline(estimators)
param_grid = [{'clf__max_depth':[2,4,7,10]}]
GridSearch = GridSearchCV(estimator=pipe, param_grid=param_grid, cv=5)
GridSearch.fit(X,y)
GridSearch.cv_results_
----------------------------------------------------------------------------
{'mean_fit_time': array([0.01302018, 0.01525412, 0.02469058, 0.03136926]),
'std_fit_time': array([0.00222836, 0.00111415, 0.00097366, 0.00195921]),
'mean_score_time': array([0.00239077, 0.00220132, 0.00239601, 0.00274467]),
'std_score_time': array([0.00049056, 0.00041199, 0.00049911, 0.00037043]),
'param_clf__max_depth': masked_array(data=[2, 4, 7, 10],
mask=[False, False, False, False],
fill_value='?',
dtype=object),
'params': [{'clf__max_depth': 2},
{'clf__max_depth': 4},
{'clf__max_depth': 7},
{'clf__max_depth': 10}],
'split0_test_score': array([0.55230769, 0.51230769, 0.50769231, 0.51692308]),
'split1_test_score': array([0.68846154, 0.63153846, 0.60461538, 0.61153846]),
'split2_test_score': array([0.71439569, 0.72363356, 0.67667436, 0.67205543]),
'split3_test_score': array([0.73210162, 0.73210162, 0.73672055, 0.71439569]),
'split4_test_score': array([0.75673595, 0.7182448 , 0.73518091, 0.72286374]),
'mean_test_score': array([0.6888005 , 0.66356523, 0.6521767 , 0.64755528]),
'std_test_score': array([0.07179934, 0.08390453, 0.08691987, 0.07629056]),
'rank_test_score': array([1, 2, 3, 4])}
import pandas as pd
score_df = pd.DataFrame(GridSearch.cv_results_)
score_df[['params', 'rank_test_score', 'mean_test_score', 'std_test_score']]
-----------------------------------------------------------------------------
params rank_test_score mean_test_score std_test_score
0 {'clf__max_depth': 2} 1 0.688800 0.071799
1 {'clf__max_depth': 4} 2 0.663565 0.083905
2 {'clf__max_depth': 7} 3 0.652177 0.086920
3 {'clf__max_depth': 10} 4 0.647555 0.076291
ROC(Receiver Operating Characteristic) Curve: FPR과 TPR의 곡선
AUC(Area Under the ROC Curve) : ROC 곡선 아래 영역