本サイトは広告・プロモーションが含まれています
Python

【初心者用】機械学習ライブラリPyCaretで回帰テスト【Python】

この記事はこんな人におすすめ

○PyCaretを試してみたい方
○回帰モデルの機械学習の勉強をしている方
○チュートリアルとは違うRegressionの例を探してる方

どうもこんにちは、コンです。
今回はTwitterなどでも少し話題になっている機械学習ライブラリ、PyCaretについて解説したいと思います。

PyCaretは、scikit-learn、XGBoost、LightGBM、CatBoost、spaCy、Opuna、Hyperopt、Ray など、いくつかの機械学習ライブラリをセットにしたライブラリだそうで、数行のコードでモデルの比較や、前処理を行えるそうです。

ただ、ニューラルネットワーク系はまだ実装されてなさそう。

Pycaret公式ページ

個人的に自動モデル選択は興味があったので
Pycaretを使ってxsin(x)関数の回帰問題を解いてみたいと思います。


PyCaretについては日経ソフトウェアさんでも扱っています。

お題

PyCaretの公式サイトには保険のデータについて
年齢、性別、bmiなどのデータから保険料を出力する回帰モデルのチュートリアルが書かれています。

今回はそれとは少し違い、下記のようなy=xsin(x)関数にノイズを加えたデータ点80個から
PyCaretでモデルを作って、モデルがどうなっているかを見てみたいと思います。

青い円で示したデータ点から予測モデルを作成する

PyCaretの実装

データ作成


PyCaretは基本的にPandasのデータフレームに対応している機械学習ライブラリなので
今回の予想お題であるxsin(x)+noiseのデータ作成もNumpyで作成しPandasのデータフレームに収納します。

下記はデータ作成用のコード。

import numpy as np
import random
import matplotlib.pyplot as plt
import pandas as pd

#予測する関数
def test_function(x):
    y = x*np.sin(x)
    return y

#機械学習用データ作成
def dataset_maker(train_n):
    #訓練データの生成
    np.random.seed(seed=16)
    x_train = np.random.rand(1, train_n)*10
    noise_train = np.random.rand(1, train_n)-0.5
    y_train = test_function(x_train)+noise_train

    return x_train, y_train

def main():
 
    x_train, y_train = dataset_maker(100)
    train_data=pd.DataFrame(
        data={'x_train': x_train.flatten(), 
          'y_train': y_train.flatten()}
    )

if __name__ == '__main__':
    main()

PyCaretによるモデル比較


PyCaretはsetupとcompare_modelsのみの記述で18種類の機械学習のモデルを評価してくれます。

先ほどのプログラムのimportとmain()/の部分に追記して実行していきます。

import numpy as np
import random
import matplotlib.pyplot as plt
import pandas as pd
from pycaret.regression import *

予測する関数
def test_function(x):
    y = x*np.sin(x)
    return y

#機械学習用データ作成
def dataset_maker(train_n):
    #訓練データの生成
    np.random.seed(seed=16)
    x_train = np.random.rand(1, train_n)*10
    noise_train = np.random.rand(1, train_n)-0.5
    y_train = test_function(x_train)+noise_train

    return x_train, y_train


def main():
    x_train, y_train = dataset_maker(100) 
    train_data=pd.DataFrame(
        data={'x_train': x_train.flatten(), 
          'y_train': y_train.flatten()}
    )
        
    s = setup(data=train_data, target = 'y_train', train_size=0.8)
    best = compare_models()

if __name__ == '__main__':
    main()

上記を実行すると、上から順に指標の良いモデルが与えられる。

どうやらExtra Trees Regressorが良い性能らしい。
大変申し訳ないのですが、決定木のアルゴリズムの1種だよ。というくらいしか知らない。。。
また今度勉強しよ。

回帰モデルをプロットしてみる


Extra Trees Regressorが1番よさそうだとわかったので、xsin(x)と共にプロットしてみて
どれくらい予想できているのか可視化してみます。

今回はLightGBMと線形回帰についても可視化してみて、性能の違いを確認してみました。

また上で説明したコードに、可視化プログラムをmain()関数に追記します。
(これで今日のコード記入は終わり)

import numpy as np
import random
import matplotlib.pyplot as plt
import pandas as pd
from pycaret.regression import *

#予測する関数
def test_function(x):
    y = x*np.sin(x)
    return y

#機械学習用データ作成
def dataset_maker(train_n):
    #訓練データの生成
    np.random.seed(seed=16)
    x_train = np.random.rand(1, train_n)*10
    noise_train = np.random.rand(1, train_n)-0.5
    y_train = test_function(x_train)+noise_train

    return x_train, y_train


def main():
    #データ生成
    x_train, y_train = dataset_maker(100)
    train_data=pd.DataFrame(
        data={'x_train': x_train.flatten(), 
          'y_train': y_train.flatten()}
    )

    #モデル比較
    s = setup(data=train_data, target = 'y_train', train_size=0.8)
    best = compare_models()
    

    x = np.linspace(0, 10, 500)
    y = test_function(x)
    #作成した回帰モデルをプロットする。
    plot_data=pd.DataFrame(
        data={'x_train': x, 
          'y_train': y}
    )

    predictions = predict_model(best, data=plot_data)
    predictions.rename(columns={'prediction_label': 'Best_function'}, inplace=True)

    #lightgbm
    lightgbm = create_model('lightgbm')
    predictions_lightgbm = predict_model(lightgbm, data=plot_data)
    predictions_lightgbm.rename(columns={'prediction_label': 'Lightgbm'}, inplace=True)
    
    #線形回帰
    lr = create_model('lr')
    predictions_lr = predict_model(lr, data=plot_data)
    predictions_lr.rename(columns={'prediction_label': 'Linear Regression'}, inplace=True)

    #pandasのフレームを結合
    df1=pd.merge(predictions, predictions_lightgbm, how='right')
    df2=pd.merge(df1, predictions_lr, how='right')
    df2.rename(columns={'y_train': 'xsin(x)'}, inplace=True)
    fig, ax = plt.subplots()
    df2.plot(x="x_train", y=['xsin(x)', 'Best_function','Lightgbm','Linear Regression'], ax=ax)  
    ax.scatter(x_train, y_train, label='train data')
    ax.set_xlabel("x")
    ax.set_ylabel("y")
    plt.show()
    plt.close()

if __name__ == '__main__':
    main()

今回のコードで個人的に難しかったのがPandasのデータフレームの取り扱いでした。
全然慣れていなかったため、列の名前を何度もrenameしております。
(読みにくくて、ごめんなさい。。。)

このコードを実行すると下図のように、xsin(x)関数と訓練に使用したデータ、Best function(Extra Trees Regressor)、LightGBM、線形回帰の回帰モデルのプロットが出力されます。

この結果からは確かにExtra Trees Regressorが他のモデルと比べて予測精度の高い回帰モデルのような気がしますね。

でも
例えばExtra Treesは良い予想モデルだけどx=0付近の値はあまり予想できていないのでは?って思ったり。
でもxが6~7にかけてはかなりスムーズな関数になっていて、良い感じなのでは?と思ったり。

機械学習の予測モデルの評価は難しい。

おわりに

ここまで読んでいただき、誠にありがとうございます。

今回はPyCaretの実装だったのですが、1番苦戦したのはPandasでした。

いつもNumpyでほとんどの事柄を行ってしまうため、Pandasの書き方わからんな〜と言いながら
フレームを結合するのに1時間くらい使ってました。

いつもと違うことをやるのも、また勉強で楽しかったです。
また機械学習のコードについて書いていきたいと思います。

COMMENT

メールアドレスが公開されることはありません。 が付いている欄は必須項目です

CAPTCHA