説明変数をポチポチ入力したら目的変数が出てくるコードを作ってみた

# はじめに
こんにちは。株式会社船井総合研究所の平尾です。
以前とある案件において、
「完成した機械学習モデルは、実際どのように使えば良いのか？」ということを
考える場面がありました。
そこで、「説明変数をポチポチ入力したら目的変数が出てくる」システムを
思い付き、Pythonで作ってみました。

# コード
### ①完成したモデルを保存
まずは完成したモデルをpickle形式で保存してください。

```
import pickle
pickle.dump(model, open(f"Qiita投稿用モデル.pickle", "wb"))
```
### ②実際に説明変数を入力して目的変数を出力させるコード

```
# A 列名とデータ型を指定してデータフレームを作成
import pickle
import pandas as pd
columns = {
    "説明変数1_int": int,
    "説明変数2_bool": bool,
    "説明変数3_bool": bool,
    "説明変数4_bool": bool,
    "説明変数5_bool": bool,
    "説明変数6_bool": bool
}

df = pd.DataFrame(columns=columns.keys())

# B 各列の値をユーザーに入力してもらう
for col, dtype in columns.items():
    while True:
        try:
            value = input(f"{col} を入力してください: ")
            if dtype == bool:
                if value.lower() == "true":
                    value = True
                    break
                elif value.lower() == "false":
                    value = False
                    break
                else:
                    raise ValueError
            else:
                value = dtype(value)
                break
        except ValueError:
            print(f"エラー: {dtype.__name__} 型の値を入力してください。")

    # データフレームに値を追加
    df.loc[0, col] = value
    
# C データ型を変換

df['説明変数1_int'] = df['説明変数1_int'].astype(int)
df['説明変数2_bool'] = df['説明変数2_bool'].astype(bool)
df['説明変数3_bool'] = df['説明変数3_bool'].astype(bool)
df['説明変数4_bool'] = df['説明変数4_bool'].astype(bool)
df['説明変数5_bool'] = df['説明変数5_bool'].astype(bool)
df['説明変数6_bool'] = df['説明変数6_bool'].astype(bool)

# D モデルを呼び出して目的変数を出力
loaded_model = pickle.load(open("Qiita投稿用モデル.pickle", "rb"))
prediction = loaded_model.predict(df)
print("目的変数：", prediction) 
```
# コード説明
### A 列名とデータ型を指定してデータフレームを作成
```
import pickle
import pandas as pd
columns = {
    "説明変数1_int": int,
    "説明変数2_bool": bool,
    "説明変数3_bool": bool,
    "説明変数4_bool": bool,
    "説明変数5_bool": bool,
    "説明変数6_bool": bool
}

df = pd.DataFrame(columns=columns.keys())
```

columnsでデータフレームの列名と、各列におけるデータ型を指定しています。
それをもとにデータフレームdfを作成します。

### B 各列の値をユーザーに入力してもらう
```
for col, dtype in columns.items():
    while True:
        try:
            value = input(f"{col} を入力してください: ")
            if dtype == bool:
                if value.lower() == "true":
                    value = True
                    break
                elif value.lower() == "false":
                    value = False
                    break
                else:
                    raise ValueError
            else:
                value = dtype(value)
                break
        except ValueError:
            print(f"エラー: {dtype.__name__} 型の値を入力してください。")

    # データフレームに値を追加
    df.loc[0, col] = value
```
各列の値をユーザーに入力してもらうためのコードがこちらです。
各列において間違った型で説明変数を入力をした場合は、
入力をやり直させるようにしています。

例えば、説明変数1_intに対して「True」と入力した場合や、
説明変数2_boolに対して「400」と入力した場合は、入力
し直す必要があります。

といっても、一度間違えたら最初からやり直しというわけではなく、
間違えたところからやり直しが利くようになっています。
そのため、「ミスらないようにしないと…！！」とハラハラドキドキしながら
入力する必要はありません。（笑）

また、value.lower()を記述しているため、
説明変数2~6_boolに対しては、大文字小文字は問いません。
そのため、入力する際はTrueでもtrueでもFalseでもfalseでもTruEでもFaLsEでも良いです。

### C データ型を変換
````
df['説明変数1_int'] = df['説明変数1_int'].astype(int)
df['説明変数2_bool'] = df['説明変数2_bool'].astype(bool)
df['説明変数3_bool'] = df['説明変数3_bool'].astype(bool)
df['説明変数4_bool'] = df['説明変数4_bool'].astype(bool)
df['説明変数5_bool'] = df['説明変数5_bool'].astype(bool)
df['説明変数6_bool'] = df['説明変数6_bool'].astype(bool)
````
ここで、データフレームの各列の型をそれぞれの適切な型に変換しています。
Bの時点でのdfの各値は全てobject型であるため、Cを実行しないとエラーが出ます。

### D モデルを呼び出して目的変数を出力
```
loaded_model = pickle.load(open("Qiita投稿用モデル.pickle", "rb"))
prediction = loaded_model.predict(df)
print("目的変数：", prediction) 
```
ここで、モデルを呼び起こしてloaded_model.predict(df)により
目的変数を計算させ、計算結果を出力させます。

# 実際の実行画面
実際にコードをターミナルで実行させると、
「～を入力してください」という表示が出力されます。
入力すると、次の指示が出力されます。

![スクリーンショット 2025-03-28 104031.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3992991/917f46dc-f5f7-4bcd-97f0-c656ea1e6499.png)


下のように、間違った型で入力した場合はエラーが出力され、再度入力を求められます。
![スクリーンショット 2025-03-28 104200.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3992991/fa2930e3-052c-4da9-a8aa-e0ed3c4729a2.png)


最後まで入力すると、下のように計算結果が出力されます。
![スクリーンショット 2025-03-28 104832.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3992991/eebab8b4-5c1a-443e-8052-94327e89da30.png)