#はじめに
モデルの汎化性能を評価する上で、より頑健な手法である交差検証を導入する。また、クラス分類性能と回帰性能を評価する上で、score
でのデフォルトのR^2よりも良い手法について議論されてます。
教師あり学習で汎化性能を最大にするように効率的にパラメータを調整するグリッドサーチにも触れます。
#交差検証
交差検証では、データの分割を何度も繰り返して行うことで、これまでのただの分割よりも安定した評価を実現する。最もよく用いられるのは、k分割交差検証である。例えば、k=5の場合は、分割0から分割4の5つに分割され、分割0から順番にテストセットに、残りの分割を訓練セットにして学習を行い、性能の平均をとる。
##(層化)k分割交差検証
from sklearn.model_selection import cross_val_score
データをk個に分割する際に、先頭から1/k個取る方法はうまくいくとは限らない。なぜなら、データがクラス0から順番に保存されているデータセットもあるためだ。そのため、scikit-learnでは各分割内でのクラスの比率が全体の比率と同じになるように、層化交差検証を行っている。
cross_val_score
では、デフォルトで3分割交差検証を行い、3つの精度を返す。
cv
分割数
##1つ抜き交差検証
from sklearn.model_selection import LeaveOneOut
k分割交差検証の個々の分割が1サンプルしかないと考え、毎回、テストセットの中の1サンプルだけをテストセットとして検証する。大規模なデータセットでは非常に時間がかかるが、小さいデータセットではよりよい推定ができる。
##シャッフル分割交差検証
from sklearn.model_selection import ShuffleSplit
データセットの中から指定した数・割合の訓練セットとテストセットを選び、指定した回数の検証を行う。サブサンプリングと呼ばれる、データの一部だけを用いるようにすることもでき、データセットが大きい場合に有用である。
train_size
訓練セットの数・割合
test_size
テストセットの数・割合
n_iter
繰り返しの回数
##グループ付き交差検証
from sklearn.model_selection import GroupKFold
汎化性能を高めるためには、データとしては異なるものの、訓練セットとテストセットに分かれることが好ましくないことがある。例えば、表情から感情を予測する際に、同じ人のデータが分かれることである。なぜならば、学習済の人の表情の予測は容易になるはずであり、未知の人の表情から感情を予測する汎化性能を計るには適切でないためである。
そのため、配列を用意し、同じグループに属するデータには同じ番号を振ることで、それらのデータをグループ化し、個々のグループはまとまって訓練セットもしくはテストセットに入るように出来る。
groups
グループ分けを行うための配列
#グリッドサーチ
グリッドサーチとは、基本的にはパラメータのすべての組み合わせに対して試して見る方法である。ただし、それぞれのパラメータに対する評価に対してテストセットを使っていては、汎化性能を適切に評価できているとは言い難い。そのため、訓練セット・検証セット・テストセットとデータセットを3つに分割する。
###交差検証を用いたグリッドサーチ
from sklearn.model_selection import GridSearchCV
グリッドサーチは一般に用いられているが、データの実際の分割のされ方によって大きく性能が変わる。そのため、それぞれのパラメータの組み合わせに対して交差検証を行うとよい。ただし、パラメータ2つをそれぞれ6つの値で、交差検証を5回行うとすると、6×6×5=180通りのモデルを訓練する必要がある。これには非常に時間がかかることが大きな問題点である。
###ネストした交差検証
上記のグリッドサーチでは、データセットを訓練セットとテストセットに一度だけ分け、訓練セット上で交差検証を行い、訓練セットと検証セットに分けた。訓練セットとテストセットの分割が一度だけの場合、その分割の仕方に結果が依存する場合がある。そのため、訓練セットとテストにも交差検証による分割を適用する。この手法をネストした交差検証と呼ぶ。
ネストした交差検証をscikit-learnで行うのは容易で、cross_val_score
をGridSearchCV
のインスタンスをモデルとして呼び出せば良い。
#評価基準とスコア
機械学習の基準を選ぶときには、そのアプリケーションによって最終的な目的を考える必要がある。横軸を予測ラベル、縦軸を新ラベルとし、あてはまるデータの数を成分とした行列を混同行列と呼ぶ。
##2クラス分類
2クラス分類では、2つのクラスを陽性と陰性と呼ぶ。予測・実際の値がともに陽性のときを真陽性(TP)、予測・実際の値がともに陰性のときを真陰性(TN)と呼ぶ。また、陽性と予測したが実際は陰性のときを偽陽性(FP)、この逆のときを**偽陰性(FN)**と呼ぶ。
from sklearn.metrics import classification_report
以下の3つの評価基準をクラスごとにそのクラスを陽性とした場合に値を出力してくれる。同時に支持度と呼ばれる、陽性のデータの数も出力してくれる。
###適合率
適合率=\frac{TP}{TP+FP}
適合率は、陽性であると予測されたものがどれだけ実際に陽性であったかを表す。偽陽性の数を制限したい場合に基準として用いられる。
###再現率
再現率=\frac{TP}{TP+FN}
再現率は、実際に陽性のデータのうち、陽性と予測されたものの割合を示す。偽陰性を避けることが重要な場合に基準として用いられる。例えば、ガンの診断。
###f-値
F=2×\frac{適合率×再現率}{適合率+再現率}
適合率と再現率がトレードオフである。すべてを陽性と判定すれば再現率は100%となるが、適合率は非常に小さくなる。一方、最も真である可能性が高いもの1つだけを真とすれば、適合率は100%となるが、再現率は非常に小さくなる。
適合率と再現率はそれぞれ非常に重要な基準であるが、一方だけでは全体像がつかめない。そのため、これら2つを包括的に評価するf-値という基準がある。これは、適合率と再現率の調和平均によって求められる。(f-値の変種の1つであり、他にもあるらしい)
###適合率・再現率カーブ
from sklearn.metrics import precision_recall_curve, average_precision_score
カーブが右上に近いほど、適合率と再現率が同時に高いため、良いクラス分類器であることがわかる。カーブを要約する方法の1つとして、カーブ下の領域(AUC)を積分することがあり、これは平均適合率とも呼ばれる。
###受信者動作特性カーブ(ROCカーブ)
from sklearn.metrics import roc_curve, roc_auc_score
横軸に偽陽性率、縦軸に**真陽性率(再現率)**をとる。低い偽陽性率を保ちながら、高い再現率を達成したいので、左上に近いほどよいクラス分類器と言える。同様にして、ROCカーブのAUCを積分することで要約することができる。
###予測の不確実性
ほとんどのクラス分類器には、予測の不確実性を評価するためのdecision_function
メソッドもしくはpredict_proba
メソッドがある。予測の閾値は、デフォルトでは前者が0、後者が0.5となっている。例えば、偽陽性が増えてもよいからより多くの真陽性を得たい場合は、閾値を小さくすることで再現率を上げることができる。
##他クラス分類
他クラス分類においても、classification_report
によって適合率・再現率・f-値を求めることができる。クラスごとのf-値を平均する方法は以下の3つがある。
macro
重みをつけずにクラスごとのf-値を平均する。個々のクラスを同じように重視している。
weighted
各クラスの支持度に応じて重みをつけてクラスごとのf-値を平均する。
micro
すべてのクラスの偽陽性・偽陰性・真陽性の総数を計算し、その値を用いて計算する。個々のサンプルを同じように重視している。
##回帰
R^2スコアが最も直観的。
#参考文献
Pythonではじめる機械学習
――scikit-learnで学ぶ特徴量エンジニアリングと機械学習の基礎
Andreas C. Muller、Sarah Guido 著、中田 秀基 訳