04. 데이터 분석 절차
part 01 ~ 03 에서 알아본 내용을 전체적으로 정리해보았다.
1) Package 설정
# 기본
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt # Graph
# 데이터 가져오기
import pandas as pd
# 데이터 전처리
from sklearn.preprocessing import StandardScaler # 연속 변수 표준화
from sklearn.preprocessing import LabelEncoder # 범주형 변수 수치화
# 훈련/검증용 데이터 분리
from sklearn.model_selection import train_test_split # 훈련과 테스트를 위한 데이터 분리
# # 분류 모델
# from sklearn.tree import DecisionTreeClassifier # 의사결정나무
# from sklearn.naive_bayes import GaussianNB # 나이브 베이즈 분류
# from sklearn.ensemble import RandomForestClassifier # 랜덤 포레스트
# from sklearn.ensemble import BaggingClassifier # 앙상블
# from sklearn.linear_model import LogisticRegression # 로지스틱 회귀분석
# from sklearn.svm import SVC # SVM(서포트벡터머신)
# from sklearn.neural_network import MLPClassifier # 다층 인공신경망
# 모델 검정
from sklearn.metrics import confusion_matrix, classification_report # 정오분류표
from sklearn.metrics import accuracy_score, precision_score, recall_score, f1_score, make_scorer # 정확도, 민감도 등
from sklearn.metrics import roc_curve # ROC 곡선
# 최적화
from sklearn.model_selection import cross_validate # 교차 타당도
from sklearn.pipeline import make_pipeline # 파이프라인 구축
from sklearn.model_selection import learning_curve, validation_curve # 학습곡선, 검증곡선
from sklearn.model_selection import GridSearchCV # 하이퍼파라미터 튜닝
2) 데이터 가져오기
2-1) 데이터 프레임으로 저장
- csv 데이터를 dataframe으로 가져오기
train = pd.read_csv('../Data/train.csv')
test = pd.read_csv('../Data/test.csv')
# train data의 상위 5개 출력
train.head()
employee_id | department | region | education | gender | recruitment_channel | no_of_trainings | age | previous_year_rating | length_of_service | awards_won? | avg_training_score | is_promoted | |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|
0 | 65438 | Sales & Marketing | region_7 | Master's & above | f | sourcing | 1 | 35 | 5.0 | 8 | 0 | 49 | 0 |
1 | 65141 | Operations | region_22 | Bachelor's | m | other | 1 | 30 | 5.0 | 4 | 0 | 60 | 0 |
2 | 7513 | Sales & Marketing | region_19 | Bachelor's | m | sourcing | 1 | 34 | 3.0 | 7 | 0 | 50 | 0 |
3 | 2542 | Sales & Marketing | region_23 | Bachelor's | m | other | 2 | 39 | 1.0 | 10 | 0 | 50 | 0 |
4 | 48945 | Technology | region_26 | Bachelor's | m | other | 1 | 45 | 3.0 | 2 | 0 | 73 | 0 |
- 자료구조 살펴보기
print(train.info())
print(test.info())
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 54808 entries, 0 to 54807
Data columns (total 13 columns):
# Column Non-Null Count Dtype
--- ------ -------------- -----
0 employee_id 54808 non-null int64
1 department 54808 non-null object
2 region 54808 non-null object
3 education 52399 non-null object
4 gender 54808 non-null object
5 recruitment_channel 54808 non-null object
6 no_of_trainings 54808 non-null int64
7 age 54808 non-null int64
8 previous_year_rating 50684 non-null float64
9 length_of_service 54808 non-null int64
10 awards_won? 54808 non-null int64
11 avg_training_score 54808 non-null int64
12 is_promoted 54808 non-null int64
dtypes: float64(1), int64(7), object(5)
memory usage: 5.4+ MB
None
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 23490 entries, 0 to 23489
Data columns (total 12 columns):
# Column Non-Null Count Dtype
--- ------ -------------- -----
0 employee_id 23490 non-null int64
1 department 23490 non-null object
2 region 23490 non-null object
3 education 22456 non-null object
4 gender 23490 non-null object
5 recruitment_channel 23490 non-null object
6 no_of_trainings 23490 non-null int64
7 age 23490 non-null int64
8 previous_year_rating 21678 non-null float64
9 length_of_service 23490 non-null int64
10 awards_won? 23490 non-null int64
11 avg_training_score 23490 non-null int64
dtypes: float64(1), int64(6), object(5)
memory usage: 2.2+ MB
None
# 배열의 행, 열의 갯수 확인
print(train.shape)
print(test.shape)
(54808, 13)
(23490, 12)
# column 값 확인
train.keys()
Index(['employee_id', 'department', 'region', 'education', 'gender',
'recruitment_channel', 'no_of_trainings', 'age', 'previous_year_rating',
'length_of_service', 'awards_won?', 'avg_training_score',
'is_promoted'],
dtype='object')
2-2) Data와 Target으로 분리
- 필요한 data만 추출
- data : X , target : y 로 분리
X = train.drop(['is_promoted'], axis=1)
X.head()
employee_id | department | region | education | gender | recruitment_channel | no_of_trainings | age | previous_year_rating | length_of_service | awards_won? | avg_training_score | |
---|---|---|---|---|---|---|---|---|---|---|---|---|
0 | 65438 | Sales & Marketing | region_7 | Master's & above | f | sourcing | 1 | 35 | 5.0 | 8 | 0 | 49 |
1 | 65141 | Operations | region_22 | Bachelor's | m | other | 1 | 30 | 5.0 | 4 | 0 | 60 |
2 | 7513 | Sales & Marketing | region_19 | Bachelor's | m | sourcing | 1 | 34 | 3.0 | 7 | 0 | 50 |
3 | 2542 | Sales & Marketing | region_23 | Bachelor's | m | other | 2 | 39 | 1.0 | 10 | 0 | 50 |
4 | 48945 | Technology | region_26 | Bachelor's | m | other | 1 | 45 | 3.0 | 2 | 0 | 73 |
y = train['is_promoted']
y.head()
0 0
1 0
2 0
3 0
4 0
Name: is_promoted, dtype: int64
3) 데이터 전처리
3-1) data(X) 레이블 인코딩
- 문자형 자료를 숫자(범주형)로 인코딩
- 숫자형 자료를 표준화
- 의사결정나무, 랜덤 포레스트, 나이브 베이즈 분류에서는 원본 데이터를 그대로 유지하면 됨
3-2) Class(Target) 레이블 인코딩
내가 가지고 있는 data의 target은 int형 값이므로 새롭게 인코딩 하지는 않았지만, 만약 레이블링 해야한다면 다음 code를 활용할 수 있다.
# class_le = LabelEncoder()
# y = class_le.fit_transform(y)
4) 훈련 / 검증용 데이터 분할
X_train, X_test, y_train, y_test = \
train_test_split(X, y,
test_size = 0.3, # test set의 비율
random_state = 1, # 무작위 시드 번호
stratify = y) # 결과 레이블의 비율대로 분리
5) 모델 구축
모델은 각각 직접 사용할 때 다시 호출하겠다.
6) 모델 검정
훈련용 데이터의 정확도와 검증용 데이터의 정확도를 비교하며 검증하는 것이 일반적이다.
이외에 검증용 데이터로 예측하는 방법도 존재한다.predict()
: class의 결과값으로 표시predict_proba()
: 확률 값으로 표시
아직 model을 선정하지도, 돌려보지도 않았기 때문에 아래의 code는 오류가 난다.
y_pred = tree.predict(X_test)
y_pred = tree.predict_proba(X_test)
정오분류표
confusion_matrix()
: table을 만듦y_test
: 실제 값 (행)y_pred
: 예측 값 (열)
confmat = pd.DataFrame(confusion_matrix(y_test, y_pred),
index=['True[0]', 'True[1]'],
columns = ['Predict[0]', 'Predict[1]'])
print('Classification Report')
print(classification_report(y_test, y_pred))
정확도, 민감도 확인
- 정밀도와 재현율은 class가 2개인 경우에만 실행
print(f'잘못 분류된 sample 갯수 : {(y_test != y_pred).sum()}')
print(f'정확도 : {accuracy_score(y_test, y_pred):.2f}%')
print(f'정밀도 : {precision_score(y_true=y_test, y_pred=y_pred):.3f}%')
print(f'재현율 : {recall_score(y_true=y_test, y_pred=y_pred):.3f}%')
print(f'F1 : {f1_score(y_true=y_test, y_pred=y_pred):.3f}%')
결과값을 해석하는 방법
정오행렬 | 분류행렬 |
---|---|
정확도 | 오류율 |
TPR | FPR |
민감도 | 특이도 |
재현율 | 정밀도 |
실제로는 같은 식을 사용하기에 아래 3가지는 같은 의미이다.
- TPR = 민감도(Sensitivity) = 재현율(Recall)
정확도는 class 0과 1 모두를 정확하게 분류함
오류율은 class 0과 1 모두를 정확하게 분류하지 못함
TPR(True Positive Rate)는 실제 class 1 중에 잘 맞춘 것을 의미
FPR(False Positive Rate)는 실제 calss 0 중에 못 맞춘 것을 의미
- 때문에 FPR은
1-FPR
로 많이 사용한다. 1-FPR
은 특이도와 같다.*
민감도는 실제 class 1 중에 잘 맞춘 것을 의미하므로 TPR과 같다.
특이도는 실제 class 0 중에 잘 맞춘 것을 의미하므로 1-FPR
이 된다.
재현율(Recall)은 실제 class 1 중에 잘 맞춘 것이므로 민감도
, TPR
과 다 동일하게 사용할 수 있다.
정밀도(Precision)은 예측 class 1 중에 잘 맞춘 것을 의미한다.
이것을 모두 합쳐 사용하는 개념이 F1
이다.
실제로 잘 맞춘 것과 예측에서도 잘 맞춘 것을 한꺼번에 계산하는 것이다.
$$F1 = 2 \times {{재현율\times정밀도} \over {재현율+정밀도}}$$
때문에 F1값이 높은 model의 성능이 뛰어나다고 이야기 할 수 있다.
ROC 곡선
- decision_function 사용이 가능한 모델일 경우 :
tree.decision_function(X_test)
- decision_function 사용이 불가능한 모델일 경우 :
tree.predict_proba(X_test)[:,1]
# 둘 중 model에 맞는 구문을 활용
# fpr, tpr, thresholes = roc_curve(y_test, tree.decision_function(X_test))
fpr, tpr, thresholes = roc_curve(y_test, tree.predict_proba(X_test)[:. 1])
# 값 확인
fpr, tpr, thresholes
# Graph 생성
plt.plot(fpr, tpr, '--', label="Decision Tree")
plt.plot([0,1], [0,1], 'k--', label="random guess")
plt.plot([fpr], [tpr], 'r--', ms=10)
plt.xlabel('FPR')
plt.ylabel('TPR')
plt.title("ROC Curve")
plt.show()
'Study > AI' 카테고리의 다른 글
03. 기계학습(머신러닝) 기초2 (0) | 2022.02.07 |
---|---|
02. 기계학습(머신러닝) 기초1 (0) | 2022.02.05 |
01. 데이터 처리 (Numpy, Pandas 기초) (0) | 2022.02.05 |
M1 Mac(Apple Silicon)에서 머신러닝 개발환경 구축하기 (0) | 2022.01.29 |
머신러닝 공부에 유용한 사이트 및 유튜브 추천 (0) | 2022.01.27 |
댓글