Pythonの機械学習用ライブラリscikit-learn
を使って,ロジスティック回帰モデルを使って簡単な分類問題にチャレンジしてみましょう.
import numpy as np
import pandas as pd
import sklearn
import seaborn as sns
import matplotlib
import matplotlib.pyplot as plt
%matplotlib inline
np.set_printoptions(precision=4)
print("numpy :", np.__version__)
print("pandas :", pd.__version__)
print("sklearn :", sklearn.__version__)
print("seaborn :", sns.__version__)
print("matplotlib :", matplotlib.__version__)
sklearn.datasets
からBreastCancerデータセットを読み込みましょう.
# make data samples
from sklearn.datasets import load_breast_cancer
bc = load_breast_cancer()
次に,pandas DataFrame()クラスのインスタンスとして,変数df_feature
, df_target
, df
を定義します.
df_data = pd.DataFrame(bc.data, columns=bc.feature_names)
df_data = df_data.loc[:, ['mean concave points', 'symmetry error', 'texture error', 'worst radius']]
df_target = pd.DataFrame(bc.target, columns=['class'])
df = pd.concat([df_data, df_target], axis=1)
df.head()
データの要約統計量(サンプル数, 平均, 標準偏差, 四分位数, 中央値, 最小値, 最大値など)をみましょう.
df.describe().T
データの共分散行列を描画します.
対角成分は自分との共分散(相関)を表すため常に1.0となります.
df.corr()
seabornを使って,共分散行列を可視化してみましょう.
データの散布図行列を描画します.
相関が大きい説明変数のペアについては, 多重共線性を考えるべきです.
sns.pairplot(df, height=2.0, diag_kind='hist', markers='+')
plt.show()
分類用のデータセットには,各データに対応するクラスラベルが与えられています.
上の散布図行列の各点を所属する3つのクラスに応じて色分けしてみましょう.
sns.pairplot(df, height=2.0, diag_kind='hist', markers='+', hue='class')
plt.show()
pandas DataFrame()クラスの変数df
から,説明変数と目的変数に相当するデータをそれぞれ取り出し,numpy.ndarray()クラスの変数X
, y
へ格納します.
X = df_data.values
y = df_target.values
y = y.reshape(-1)
全データをtrainデータとtestデータに分割します.
すなわち,変数X
をX_train
とX_test
に,
変数y
をy_train
とy_test
に分けます.
# split data by Hold-out-method
from sklearn.model_selection import train_test_split
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=0)
print()
で配列の形状を確認してみましょう.
print("X_train: ", X_train.shape)
print("y_train: ", y_train.shape)
print("X_test: ", X_test.shape)
print("y_test: ", y_test.shape)
# Logistic Regression
from sklearn.linear_model import LogisticRegression
clf_lr = LogisticRegression(random_state=0,
solver='lbfgs',
multi_class='auto')
# fit
clf_lr.fit(X_train, y_train)
# predictions
y_train_pred = clf_lr.predict(X_train)
y_test_pred = clf_lr.predict(X_test)
# Accuracy
from sklearn.metrics import accuracy_score
print('Accuracy (train) : {:>.4f}'.format(accuracy_score(y_train, y_train_pred)))
print('Accuracy (test) : {:>.4f}'.format(accuracy_score(y_test, y_test_pred)))
混同行列(Confusion matrix)を描画してみましょう.
# Confusion matrix
from sklearn.metrics import confusion_matrix
cmat_train = confusion_matrix(y_train, y_train_pred)
cmat_test = confusion_matrix(y_test, y_test_pred)
def print_confusion_matrix(confusion_matrix, class_names, plt_title='Confusion matrix: ', cmap='BuGn', figsize = (6.25, 5), fontsize=10):
df_cm = pd.DataFrame(confusion_matrix, index=class_names, columns=class_names)
fig = plt.figure(figsize=figsize)
heatmap = sns.heatmap(df_cm, annot=True, fmt="d", cmap=cmap)
heatmap.yaxis.set_ticklabels(heatmap.yaxis.get_ticklabels(), rotation=0, ha='right', fontsize=fontsize)
heatmap.xaxis.set_ticklabels(heatmap.xaxis.get_ticklabels(), rotation=45, ha='right', fontsize=fontsize)
plt.xlabel('Predicted label')
plt.ylabel('True label')
plt.title(plt_title, fontsize=fontsize*1.25)
plt.show()
print_confusion_matrix(cmat_train,
bc.target_names,
plt_title='Confusion matrix (train, 455 samples)')
print_confusion_matrix(cmat_test,
bc.target_names,
plt_title='Confusion matrix (test, 114 samples)')