JavaScriptを有効にしてください

Scikit-learnのGridSearchCVクラスによるグリッドサーチ

 ·   5 min read

はじめに

機械学習モデルのハイパーパラメータ(ユーザが決めるべきパラメータ)を調整する手法の1つにグリッドサーチ (grid search) があります。グリッドサーチでは、ハイパーパラメータの値の候補を用意して、総当たりで最良の値を見つけます。

この記事ではPythonとScikit-learnによるサンプルコードも示します。実行環境は以下の通りです。

  • Python: 3.9.7
  • NumPy: 1.20.3
  • sklearn: 0.24.2

グリッドサーチの例

ランダムフォレストを対象にグリッドサーチの例を示します。ランダムフォレストの2つのハイパーパラメータである「木の数」と「木の最大深さ」について、それぞれ以下の候補から予測性能が最良となる値を選択するものとします。

  • 木の数: 5, 10, 15
  • 木の最大深さ:2, 4, 6

それぞれ3通りなので、合計で3×3=9回の学習と検証を行って精度を評価し、最も精度が良い「木の数」と「木の最大深さ」を選びます。以上がグリッドサーチの例です。

データの分割

グリッドサーチを行うとき、検証データに注意します。例えば以下のようにデータを3分割します。

  1. 学習用データ
  2. グリッドサーチ用の検証データ
  3. 最終的にハイパーパラメータを選択したモデル用の検証データ

まず、1と2のデータでグリッドサーチを行って、ハイパーパラメータを選択します。最後に3のデータで精度を検証します。これが未知データに対して期待される予測モデルの性能になります。というのも、グリッドサーチによって得られたハイパーパラメータは、グリッドサーチに使用した検証データに対して過剰適合している可能性があるためです。

scikit-learnのグリッドサーチ

scikit-learnではsklearn.model_selection.GridSearchCVというクラスに、グリッドサーチと交差検証が実装されています。

1
2
class sklearn.model_selection.GridSearchCV(estimator, param_grid, 
    scoring=None, n_jobs=None, refit=True, cv=None, verbose=0)

主なパラメータの意味は以下の通りです。

  • estimator (estimator object): scikit-learnの予測モデル(回帰、分類、クラスタリング)のオブジェクト。
  • param_grid (dict): 探索したい予測モデルのパラメータ。
  • scoring (str etc.): 予測モデルを評価する指標(下表参照)。
  • n_jobs (int): 並列計算数。-1にすると全てのCPUコアを使用。デフォルトのNone1になる。
  • refit (bool): True(デフォルト)の場合、交差検証後に、全データを用いて最適なパラメータを使ったモデルを学習させる。
  • cv (int): 交差検証の回数。デフォルトはNoneで、5回交差検証を行う。
  • verbose (int): 実行中のメッセージの詳細度合い。0~3の範囲を取り、数値が大きいほど詳細になる。デフォルトは0.

scoringで指定できる指標の一部を示します。

分類分類モデルの評価も参考にしてください)

scoring 意味
accuracy 正解率
f1 F値
precision 適合率
recall 再現率
roc_auc ROC曲線の下側の面積

回帰回帰モデルの評価も参考にしてください)

scoring 意味
max_error 最大誤差
neg_mean_absolute_error 平均絶対誤差
neg_mean_squared_error 平均二乗誤差
neg_mean_absolute_percentage_error 平均絶対パーセント誤差

また、主なメソッドは以下の通りです。

  • fit(X[, y]): 交差検証を行う。Xは特徴量データ、yは目的変数データ(クラスタリングの場合は省略)。
  • predict(X): (fit()で交差検証を実行した後に)最適なパラメータのモデルで予測を行う(refit=Trueとする必要がある)。

GridSearchCVクラスの使用例

GridSearchCVクラスの使用例を示します。ランダムフォレストによる分類モデルRandomForestClassifierクラスに対して、グリッドサーチと交差検証を行います。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
import numpy as np
from sklearn.ensemble import RandomForestClassifier
from sklearn.model_selection import GridSearchCV

np.random.seed(0)
X = np.linspace(1,100,num=100).reshape(100,-1)*np.random.rand(100, 2)
y = np.array([0]*50+[1]*50)

rfc = RandomForestClassifier(n_estimators=5)
parameters = {"criterion": ["gini", "entropy"],
              "max_depth": [3, 5, 7]}

gscv = GridSearchCV(rfc, parameters, scoring="roc_auc", cv=3)
gscv.fit(X, y)

まず、交差検証に使用するデータX, yを作成します。Xは説明変数の配列(サンプル数100, 特徴量数2)、yはクラスを示す変数です。

次に、RandomForestClassifierクラスのオブジェクトを作成します。ここでは、木の数n_estimatorsは5で固定しています。parametersに探索したいパラメータとその候補を記述しています。分類の指標criterionが2種類、木の最大深さmax_depthが3種類で、合計2×3=6通りの組み合わせを探索します。

GridSearchCVには、ランダムフォレストのオブジェクトと、探索したいパラメータを設定します。ここで、パラメータ探索の指標scoringは、roc_aucとしています。また、交差検証の数cvは3としました。すなわち、あるパラメータの組み合わせに対して、学習データと検証データの組み合わせを変えた評価を3回行います。

fit()メソッドによるグリッドサーチ・交差検証の完了後、最適なパラメータの組み合わせはbest_params_に格納されます。

1
print(gscv.best_params_)

実行結果

1
{'criterion': 'gini', 'max_depth': 3}

これらの最適なパラメータを用いたランダムフォレストのモデルは、gscv.best_estimator_に格納されています。

1
print(gscv.best_estimator_)

実行結果

1
RandomForestClassifier(max_depth=3, n_estimators=5)

このモデルによる予測結果を得たい場合は、predict()メソッドを使用します(モデルはfit()メソッドに使用したデータで学習されています。また、refit=Trueとしている必要があります)。

1
y_pred = gscv.predict(X)

さらに、最適なパラメータを用いたモデルの評価指標(ここではROC曲線の下側の面積roc_auc)は、best_score_に格納されています。

1
print(gscv.best_score_)

実行結果

1
0.9270833333333334

参考

シェアする

Helve
WRITTEN BY
Helve
関西在住、電機メーカ勤務のエンジニア。X(旧Twitter)で新着記事を配信中です

サイト内検索