今回は、scikit-learnのSVMを使って、入門編としてXOR演算を学習させました。ついに機械学習の章に入ってきて、テンションも上がります。最近実践中心だったので、基礎からもう一度学び直したいと思います。
Pythonによるスクレイピング&機械学習開発テクニック増補改訂 Scrapy、BeautifulSoup、scik [ クジラ飛行机 ]の第4章を参考にさせていただきながら、取り組んでいます。
環境構築については、Dockerを使われる方は、以下をご参照ください。
OSから、Ubuntuを導入して取り組む方は、以下をご参照ください。
では、振り返っていきたいと思います。
scikit-learnは、Pythonで提供されている機械学習のフレームワークです。scikit-learnでは、機械学習用の様々なツールが用意してあり、教師あり学習の分類や回帰から、教師なし学習のクラスタリングや次元削減まで、手軽に実施することができます。また、ツールだけでなく機械学習を試すためのサンプルデータも用意されているところが嬉しいです。 インストールされていない場合は、以下でインストールできます。 pip3 install scikit-learn 公式サイトは、以下にありますので、必要に応じご参照ください。 では、入門編として、単純なXOR演算を学習するモデルを作成して行きます。 XOR演算は、図1.のように両方とも0または両方とも1の時は0を出力し、どちらか片方が0でもう片方が1の場合は1を出力する演算です。 これは、入力PとQの組み合わせにより、出力が1、0に分類される、分類問題と捉えることができます。 上記の入出力データを訓練データとして学習し、XORの処理が行えるモデルを構築します。 コード全体は以下の通りで、「xor-train.py」に保存しました。 from sklearn import svm # (1)XOR の演算結果(訓練データ)の作成 #(2)学習するためにデータとラベルに分割 #(4)データを予測 #(5)予測結果がラベルと合っているか確認 total=0 print('正解率:', ok, '/', total, '=', ok/total) では、コードを順番に見ていきます。 XOR演算の結果を訓練データとして格納します。今回は、pandasを使わず、入力データと出力データの組み合わせを一つのリストとして、それぞれの組み合わせをさらにリストにする入れ子形式のリストを作成しています。 xor_data = [ 先ほど作成したxor_dataを、学習用のデータと、正解のラベルに分割します。 最初からデータとラベルを分けていないのは、実際の業務や、kaggleなどのコンペでは、あらかじめ正解ラベルがあるわけではなく、一連のデータの中から、求める目的変数を特定して訓練データと正解ラベルに分ける処理が基本になるので、その処理も含めています。(実際はpandasで扱うので、for文を書くことはほとんど無いですが。) 今回の分割では、for文でxor_dataから、1行ずつ入出力の組み合わせを取り出して、入力データをdataに追加(append)、出力データをlabelに追加しています。 data = まずは、scikit-learnからインポートしたsvm(サポートベクターマシン)のモジュールから、SVC(Support Vector Classification)のクラスを呼び出して、サポートベクターマシンを使った分類ができるモデルの実体を作ります。 サポートベクターマシンについては、改めて復習したいと思いますが、今回は、中身がわからなくても手軽に機械学習ができるというところがポイントなので割愛します。 clf = svm.SVC() モデルの実体ができたら、あとは、fit()メソッドを使って、訓練データ(data)と正解ラベル(label)を引数に渡して実行するだけで、学習は完了です。 clf.fit(data, label) 複雑なデータになると前処理や、特徴量分析などが必要になりますが、機械学習自体は、モデルの実体を作って、学習を実行するという処理で学習が完了できるのは、とても刺激的でした。(もちろん、精度を上げるためには、前処理や特徴量分析が大変になりますが…。) では、早速、先ほど学習したモデル(clf)を使って、予測を行います。 予測についても学習と同様に簡単で、predict()メソッドに入力データを渡すことで、予測した結果を出力してくれます。 pred = clf.predict(data) 一見、学習時に、それぞれの入力に対する出力結果を記憶していただけのようにも見えますが、実際は、入力データから出力データを算出する処理が動いています。 先ほど予測した予測結果(pred)を順番に正解ラベル(label)と比較していきます。 まずは、正解数と、データの総数を格納する変数を初期化(0にする)します。 ok = 0 次に、正解ラベル(label)を一つずつanswerに取り出します。 この時、enumerate関数を使用して、idxに何番目のデータかの情報も格納します。 for idx, answer in enumerate(label): 同じidxの予測結果を取り出して、正解ラベル(answer)と同じであれば、正解数(ok)を1増やします。 p = pred[idx] 正解不正解に関わらず、データの総数は1増やします。 total +=1 最後に、正解数と、データ総数と、正解数をデータ総数で割った正解率を出力します。 print('正解率:', ok, '/', total, '=', ok/total) 先ほど作成したファイルを実行してみます。 python3 xor-train.py 以下の通り、XOR演算をsvm.SVC()を使って、学習、予測、出力することができました。 結果としては、正解数4で、データ総数も4なので、100%の正解率とすることができました。 学生時代に、XORの処理をプログラミングする課題があり、中身を考えて順番に処理を工夫していました。 しかしながら、機械学習を使えば、こんなに簡単に正解率100%のモデルを作ることができました! 実際のモデル構築時は、ここまで単純なデータではないですし、予測したいデータは、正解ラベルの無いデータであることが多いので、こんなに簡単にはいかないですが、機械学習のメリットは十分に再確認できました。 次回以降も、Pythonによるスクレイピング&機械学習開発テクニック増補改訂 Scrapy、BeautifulSoup、scik [ クジラ飛行机 ]で、スクレイピングと機械学習開発に取り組んでいきたいと思います。 【過去記事】 2019年8月31日(土)にE資格を受験して、合格しました! E資格対策として勉強の進め方や、参考書などをまとめました。 これから受験される方がいらっしゃいましたらご参考まで。 2019年3月9日(土)にG検定を受験し、見事合格できました! 受験の体験記や勉強法などを別のブログにまとめました。 これから受験される方がいらっしゃいましたらご参考まで。 【E資格対策に使った参考書】 scikit-learnのSVMを使ってXOR演算を学習させる。
1.scikit-learnとは何か
2.全体像
xor_data = [
#P, Q, result
[0, 0, 0],
[0, 1, 1],
[1, 0, 1],
[1, 1, 0]
]
data =
label =
for row in xor_data:
p = row[0]
q = row[1]
r = row[2]
data.append([p,q])
label.append(r)
#(3)学習を実施
clf = svm.SVC()
clf.fit(data, label)
pred = clf.predict(data)
print('予測結果:', pred)
ok = 0
for idx, answer in enumerate(label):
p = pred[idx]
if p == answer: ok += 1
total +=13.XOR の演算結果(訓練データ)の作成
#P, Q, result
[0, 0, 0],
[0, 1, 1],
[1, 0, 1],
[1, 1, 0]
]4.学習するためにデータとラベルに分割
label =
for row in xor_data:
p = row[0]
q = row[1]
r = row[2]
data.append([p,q])
label.append(r)5.学習を実施
6.データを予測
print('予測結果:', pred)7.予測結果がラベルと合っているか確認
total=0
if p == answer: ok += 1
8.コマンドラインから実行してみる。