初心者向け機械学習サンプルソース

www.headboost.jp

#最も使われているのはGoogleが公開しているTensorFlow(テンサーフロー)か、scikit-learn(サイキットラーン)でしょう。

from sklearn import datasets #scikit-learnのデータセットモジュールのインポート
digits=datasets.load_digits() #手書き数字のデータセットの読み込み

print(dir(digits))
#['DESCR', 'data', 'images', 'target', 'target_names']
#名前    データの内容
#DESCR データセットの説明文
#data  画像データ(訓練データとテストデータ)
#images    画像データ(8行×8列にしたもの)
#target    画像データの答えとなる数字(教師データと検証用データ)
#target_names  targetの画像データの数字の名前(数字の種類)
print(digits.DESCR)

#shape は,スカラーや,タプルによって配列の各次元の大きさを表す属性です.
print(digits.data.shape)
#(1797, 64)#8x8が1797文字分
print(digits.target.shape)
#(1797,)#1797文字分の答え
print(digits.images.shape)
#(1797, 8, 8)#8x8の文字1797個のイメージ
print(digits.target_names.shape)
#(10,)#答えの種類

#画像データ
print(digits.images[0])
#[[ 0.  0.  5. 13.  9.  1.  0.  0.]
# [ 0.  0. 13. 15. 10. 15.  5.  0.]
# [ 0.  3. 15.  2.  0. 11.  8.  0.]
# [ 0.  4. 12.  0.  0.  8.  8.  0.]
# [ 0.  5.  8.  0.  0.  9.  8.  0.]
# [ 0.  4. 11.  0.  1. 12.  7.  0.]
# [ 0.  2. 14.  5. 10. 12.  0.  0.]
# [ 0.  0.  6. 13. 10.  0.  0.  0.]]

#Matshow: 2次元配列を表示する。
import matplotlib.pyplot as plt
plt.matshow(digits.images[1], cmap="Greys")
#plt.show()

#答えの種類
print(digits.target_names)
#[0 1 2 3 4 5 6 7 8 9]

#データを分ける
n=len(digits.data)*1//2 #データを半分にわける
print(n)
#//     a//b    aをbで割った商の整数値
#リスト[開始位置:終了位置:スライス]
X_training = digits.data[:n] #dataの前半分
Y_training = digits.target[:n] #targetの前半分
X_test = digits.data[n:] #dataの後半分
Y_test = digits.target[n:] #targetの後半分

#上記確認
print([i.shape for i in [X_training, Y_training, X_test, Y_test]])
#[(898, 64), (898,), (899, 64), (899,)]

#scikit-learnのライブラリにあるsvmモジュールのSVCというアルゴリズムを使います。
#Classification
#Regression
#Clustering
#Dimensionality reduction
#Model selection
#Preprocessing
#svmモジュールは、この中のClassification(データの特徴を分析して、カテゴリー毎に分類する学習アルゴリズム)です
#=============================
#  学習
#=============================
from sklearn import svm #svmモジュールをインポート
lng = svm.SVC(gamma=0.001) #学習器を作る
#SVC関数の引数のgammaは、関数計算のカーネル係数です。
lng.fit(X_training, Y_training) #学習器に訓練データと教師データを渡す

#=============================
#  テスト
#=============================
#テストデータを使って性能を評価する
print(lng.score(X_test, Y_test))
#0.9688542825361512

#学習器にpredict()メソッドを実行すると、次のようにテストデータの識別結果を numpy の配列で返してくれます
predicted = lng.predict(X_test) #判別結果をNumpy配列で取り出す
print(predicted)
#[8 8 4 9 0 8 9 8 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 9 6 7 8 9
# 0 9 5 5 6 5 0 9 8 9 8 4 1 7 7 3 9 1 2 7 8 2 0 1 2 6 3 3 7 3 3 4 6 6 6 4 9
# 1 5 0 9 5 2 8 2 0 0 1 7 6 3 2 1 4 6 3 1 3 9 1 7 6 8 4 3 1 4 0 5 3 6 9 6 1
# 7 5 4 4 7 2 8 2 2 5 7 9 5 4 4 9 0 8 9 8 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6
# 7 8 9 0 1 2 3 4 5 6 7 8 9 0 9 5 5 6 5 0 9 8 9 8 4 1 7 7 3 5 1 0 0 7 8 2 0
# 1 2 6 3 3 7 3 3 4 6 6 6 9 9 1 5 0 9 5 2 8 2 0 0 1 7 6 3 2 1 5 4 6 3 1 7 9
# 1 7 6 8 4 3 1 4 0 5 3 6 9 6 1 7 5 4 4 7 2 8 2 2 5 7 9 5 4 8 8 4 9 0 8 9 8
# 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 9 5 5 6 5 0
# 9 8 9 8 4 1 7 7 3 5 1 0 0 2 2 7 8 2 0 1 2 6 3 3 7 3 3 4 6 6 6 4 9 1 5 0 9
# 5 2 8 2 0 0 1 7 6 3 2 2 7 4 6 3 1 3 9 1 7 6 8 4 3 1 4 0 5 3 6 9 6 8 7 5 4
# 4 7 2 8 2 2 5 7 9 5 4 8 8 4 9 0 8 9 8 0 9 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7
# 8 9 0 1 2 3 4 5 6 7 8 9 0 9 5 5 6 5 0 9 8 9 8 4 1 7 7 3 5 1 0 0 2 2 7 8 2
# 0 1 2 6 3 3 7 3 3 4 6 6 6 4 9 1 5 0 9 6 2 8 3 0 0 1 7 6 3 2 1 7 4 6 3 1 3
# 9 1 7 6 8 4 3 1 4 0 5 3 6 9 6 1 7 5 4 4 7 2 8 2 2 5 7 9 5 4 8 8 4 9 0 8 0
# 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 9 5 5 6 5 0 9
# 8 9 8 4 1 7 7 3 5 1 0 0 2 2 7 8 2 0 1 2 6 3 3 7 3 3 4 6 6 6 4 9 1 5 0 9 5
# 2 8 2 0 0 1 7 6 3 2 1 7 4 6 3 1 3 9 1 7 6 8 4 3 1 4 0 5 3 6 9 6 1 7 5 4 4
# 7 2 8 2 2 5 7 9 5 4 8 8 4 9 0 8 9 8 0 1 2 3 4 5 1 7 8 9 0 1 2 3 4 5 6 9 0
# 1 2 3 4 5 6 7 8 9 4 9 5 5 6 5 0 9 8 9 8 4 1 7 7 3 5 1 0 0 2 2 7 8 2 0 1 2
# 6 8 7 7 7 3 4 6 6 6 9 9 1 5 0 9 5 2 8 0 1 7 6 3 2 1 7 9 6 3 1 3 9 1 7 6 8
# 4 3 1 4 0 5 3 6 9 6 1 7 5 4 4 7 2 2 5 7 3 5 9 4 5 0 8 9 8 0 1 2 3 4 5 6 7
# 8 9 0 1 2 8 4 5 6 7 8 9 0 1 2 5 4 5 6 7 8 9 0 9 5 5 6 5 0 9 8 9 8 4 1 7 7
# 7 5 1 0 0 2 2 7 8 2 0 1 2 6 8 8 7 5 8 4 6 6 6 4 9 1 5 0 9 5 2 8 2 0 0 1 7
# 6 3 2 1 7 4 6 3 1 3 9 1 7 6 8 4 5 1 4 0 5 3 6 9 6 1 7 5 4 4 7 2 8 2 2 5 7
# 9 5 4 8 8 4 9 0 8 9 8]

print((Y_test != predicted).sum()) #教師データと一致しなかった数(誤答数)を合計
#numPy同士の演算
#https://www.headboost.jp/python-numpy-array-calculations/
#28

#sklearnモジュールのmetrics()メソッドのmetrics.classification_report()を使うと、それぞれの数字の正答率がわかります。
from sklearn import metrics
print(metrics.classification_report(Y_test, predicted))
#              precision    recall  f1-score   support
#
#           0       1.00      0.99      0.99        88
#           1       0.99      0.97      0.98        91
#           2       0.99      0.99      0.99        86
#           3       0.98      0.87      0.92        91
#           4       0.99      0.96      0.97        92
#           5       0.95      0.97      0.96        91
#           6       0.99      0.99      0.99        91
#           7       0.96      0.99      0.97        89
#           8       0.94      1.00      0.97        88
#           9       0.93      0.98      0.95        92
#
#    accuracy                           0.97       899
#   macro avg       0.97      0.97      0.97       899
#weighted avg       0.97      0.97      0.97       899
#precision:正答率
#recall:再現率
#f1-score:F値
#support:個数
#例えば、人工知能がある手書き画像を「4」であると判別したとします。
#その時、実際に「4」だった正答率が98%です。
#そして、「4」の手書き画像を「4」と正しく分類できた割合が再現率である95%です。
#F値は判別結果の統計的な有効性です。

#metrics.confusion_matrix()を使うと、各文字ごとの正答数と誤答数がわかります。
#引数には教師データとpredicted()メソッドで作った判別結果を渡します。
from sklearn import metrics
print(metrics.confusion_matrix(Y_test, predicted))
#[[87  0  0  0  1  0  0  0  0  0]
# [ 0 88  1  0  0  0  0  0  1  1]
# [ 0  0 85  1  0  0  0  0  0  0]
# [ 0  0  0 79  0  3  0  4  5  0]
# [ 0  0  0  0 88  0  0  0  0  4]
# [ 0  0  0  0  0 88  1  0  0  2]
# [ 0  1  0  0  0  0 90  0  0  0]
# [ 0  0  0  0  0  1  0 88  0  0]
# [ 0  0  0  0  0  0  0  0 88  0]
# [ 0  0  0  1  0  1  0  0  0 90]]
#1行目が「0」で最後の10行目が「9」です。そして1列目が「0」で最後の10列目が「9」です。
#1行目は「0」の判別結果です。87個正解して1個を「4」と誤答したことがわかります

#それでは間違いが多かった箇所の手書き数字の画像と、判別結果を表示してみましょう。
import matplotlib.pyplot as plt
imgs_yt_preds = list(zip(digits.images[n:], Y_test, predicted))
for index, (image, y_t, pred) in enumerate(imgs_yt_preds[704:716]):
    plt.subplot(3, 4, index+1)
    plt.axis('off')
    plt.tight_layout()
    plt.imshow(image, cmap="Greys", interpolation="nearest")
    plt.title(f'right:{y_t} result:{pred}', fontsize=12)
plt.show()
#アヤメの品種判別の機械学習
from sklearn import datasets
from sklearn import svm
iris = datasets.load_iris() #データセッtの読み込み
X=iris.data #訓練/テストデータ
Y=iris.target #教師データ

from sklearn.model_selection import ShuffleSplit
ss = ShuffleSplit(train_size=0.5, test_size=0.5, random_state=0)
#ShuffleSplit(ランダム置換相互検証)
#概要
#独立した訓練用・テスト用のデータ分割セットを指定した数だけ生成する.
#データを最初にシャッフルしてから,訓練用とテスト用にデータを分割する.
#オプション(引数)
#n_splits:生成する分割セット数
#test_size:テストに使うデータの割合(0~1の間で指定)
#random_state:シャッフルする時の乱数のシード
train_index, test_index = next(ss.split(X))
print(train_index)
#[  3 149  98   6  68 109  96  12 102 120 104 128  46  11 110 124  41 148
#   1 113 139  42   4 129  17  38   5  53 143 105   0  34  28  55  75  35
#  23  74  31 118  57 131  65  32 138  14 122  19  29 130  49 136  99  82
#  79 115 145  72  77  25  81 140 142  39  58  88  70  87  36  21   9 103
#  67 117  47]
print(test_index)
#[114  62  33 107   7 100  40  86  76  71 134  51  73  54  63  37  78  90
#  45  16 121  66  24   8 126  22  44  97  93  26 137  84  27 127 132  59
#  18  83  61  92 112   2 141  43  10  60 116 144 119 108  69 135  56  80
# 123 133 106 146  50 147  85  30 101  94  64  89  91 125  48  13 111  95
#  20  15  52]
X_train, Y_train = X[train_index], Y[train_index] #訓練データ
X_test, Y_test = X[test_index], Y[test_index] #テストデータ

#=================
#学習
#=================
lng = svm.SVC()
lng.fit(X_train, Y_train)
#=================
#評価
#=================
print(lng.score(X_test, Y_test))

一致率の低い例

#アヤメの品種判別の機械学習
from sklearn import datasets
iris = datasets.load_iris() #irisデータセットの読み込み
print(dir(iris))
#['DESCR', 'data', 'feature_names', 'filename', 'frame', 'target', 'target_names']
print(iris.DESCR)
X = iris.data #訓練/テストデータ
Y = iris.target #教師データ
print(X.shape)
print(Y.shape)
#(150, 4)
#(150,)
print(X)
print(iris.feature_names)
#['sepal length (cm)', 'sepal width (cm)', 'petal length (cm)', 'petal width (cm)']
#このように、sepal length(がく片の長さ)、sepal width(がく片の幅)、 petal length(花弁の長さ)、 petal width(花弁の幅)の4つの属性があることがわかります。
print(Y)
#[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
# 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
# 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 2 2 2 2 2 2 2 2 2 2
# 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2
# 2 2]
#0はsetosa、1はversicolour、2はvirginicaです。

#入っているデータを散布図で視覚化すると次のようになります(がく片の長さがx軸とがく片の幅がy軸)。
import matplotlib.pyplot as plt
plt.scatter(X[:50, 0], X[:50, 1], color='r', marker='^', label='setosa')
plt.scatter(X[50:100, 0], X[50:100, 1], color='g', marker='+', label='versicolour')
plt.scatter(X[100:, 0], X[100:, 1], color='b', marker='x', label='virginica')
plt.title("Iris Plants Database")
plt.xlabel('sepal length(cm)')
plt.ylabel('sepal width(cm)')
plt.legend()
#plt.show()

#花弁の幅をx軸、花弁の長さをy軸にとった散布図では次のようになります。
import matplotlib.pyplot as plt
plt.scatter(X[:50, 2], X[:50, 3], color='r', marker='^', label='setosa')
plt.scatter(X[50:100, 2], X[50:100, 3], color='g', marker='+', label='versicolour')
plt.scatter(X[100:, 2], X[100:, 3], color='b', marker='x', label='virginica')
plt.title("Iris Plants Database")
plt.xlabel('petal length(cm)')
plt.ylabel('petal width(cm)')
plt.legend()
#plt.show()
#====================
#学習開始
#====================
#from sklearn import datasets
from sklearn import svm
iris = datasets.load_iris() #データセッtの読み込み
X=iris.data #訓練/テストデータ
Y=iris.target #教師データ
n = len(X)//2 #データを半分に分割
X_training, X_test = X[:n], X[n:] #dataの前半分を訓練データ、後半分をテストデータに
Y_training, Y_test = Y[:n], Y[n:] #教師データを前半分と後半分に分ける
lng = svm.SVC() #学習モデル
lng.fit(X_training, Y_training) #データを学習器にかける
#====================
#テスト
#====================
print(lng.score(X_test, Y_test))
#0.3333333333333333
#正解率33%なのはデータの分割に誤りがある。

#scikit-learnのShuffleSplitメソッドを使用
from sklearn.model_selection import ShuffleSplit
ss = ShuffleSplit(train_size=0.5, test_size=0.5, random_state=0)

train_index, test_index = next(ss.split(X))
X_train, Y_train = X[train_index], Y[train_index] #訓練データ
X_test, Y_test = X[test_index], Y[test_index] #テストデータ
#====================
#学習開始
#====================
lng = svm.SVC()
lng.fit(X_train, Y_train)
print(lng.score(X_test, Y_test))
#0.9466666666666667

簡単に機械学習

qiita.com