WOE(Weight of Evidence)は、カテゴリ変数や連続変数をモデルに適した数値データに変換する手法です。この技術は、特にロジスティック回帰などの線形モデルの精度向上に有効です。本記事では、WOE変換の基本概念や利点を詳しく解説し、その実装例も紹介します。
WOE(Weight of Evidence)とは?
WOE変換の基本概念
WOE(Weight of Evidence)は、カテゴリ変数を数値に変換するための手法で、特にロジスティック回帰のような線形モデルにおいて有用です。各カテゴリの情報をバイナリアウトカムに基づいて「証拠の重み」として計算し、それを数値化します。この数値化によって、モデルがデータの情報をより効果的に取り込むことが可能になります。また、WOE変換は、カテゴリ変数の扱いにおいて線形関係を維持することができ、線形モデルでの使用に適しています。たとえば、カテゴリ変数が異なる確率でターゲット変数に影響を与える場合、その重みを計算することで特徴量の違いを強調することができます。
WOE変換はまた、外れ値や極端な値に対する耐性を持つため、モデルの頑健性を高める効果もあります。これにより、モデルのパフォーマンスが向上し、特にデータの分布が偏っている場合や、カテゴリの数が多い場合に有効です。さらに、WOEはカテゴリ変数に基づく特徴量を数値的に解釈しやすくするため、特徴量選択やモデルのチューニングにおいても効果的に利用できます。
WOEは連続値変数にも適用できますが、この場合はまず連続値をいくつかのビン(区間)に分割し、それぞれのビンに対してWOEを計算します。この手法は、連続値変数を離散化することにより、それぞれの区間に含まれるデータの分布を基にしてターゲット変数との関係を捉えることができます。ビニングには等間隔ビニングや分位数に基づくビニングなどが使用され、各ビンごとにターゲット変数の発生率が異なることから、それに基づくWOE値を算出します。このようにして連続値変数を離散化した後、各ビンにWOEを適用することで、線形モデルで連続値変数を効果的に利用できるようになります。さらに、ビニングによるWOE変換は、非線形な関係を間接的に捉えたり、外れ値の影響を減らすことに寄与します。
このように、WOEはカテゴリ変数だけでなく連続値変数にも適用することができ、それによってデータの情報を効率的に取り込むことが可能です。連続値変数のビニングとWOEの組み合わせにより、モデルがより多くの情報を学習でき、結果として予測精度の向上に繋がります。
変数値を離散化し、線形に並べ替えることで非線形な変数を線形で扱う方法
WOE変換では、非線形なカテゴリ変数を離散化し、それを線形に並べ替えることにより、線形モデルで効果的に扱うことが可能です。例えば、マーケティングキャンペーンにおいて顧客の年齢を複数のカテゴリに分けることが考えられます。次のようなカテゴリに分け、それぞれにWOEスコアを計算します。
- 18〜25歳:WOE = -0.3
- 26〜35歳:WOE = 0.1
- 36〜50歳:WOE = 0.5
- 51歳以上:WOE = 0.2
このように年齢をカテゴリに分けることで、マーケティングのターゲット層がどのように反応するかをより効果的にモデル化できます。数式で示すと、各カテゴリ に対して、WOEスコア を用いて次のように変換されます:
このプロセスにより、もともと非線形であった年齢の影響を線形な形式でモデルに取り込むことができ、結果としてモデルの精度を向上させることが可能です。特に、マーケティングやリスク分析などの分野では、こうしたカテゴリ化とWOE変換が、顧客の行動やリスクプロファイルを効果的に評価するために役立ちます。
WOEが機械学習(ロジスティック回帰)において有用である理由
WOE変換を使用することで、カテゴリ変数の影響をロジスティック回帰モデルで直接的に扱うことができます。また、WOEはカテゴリ変数の分布とターゲット変数の関係性を把握するため、モデルの解釈性を高める効果もあります。これにより、WOE変換はモデリングの前処理として強力なツールとなります。例えば、WOE変換を使用することで、カテゴリ変数の各レベルがターゲット変数にどのように影響するかを視覚的に理解することが可能です。この特性により、データサイエンティストはモデルの挙動をより深く理解し、より良い意思決定を行うことができます。
さらに、WOE変換は特にバイナリ分類の文脈で有用であり、カテゴリ変数の「良い」状態と「悪い」状態の比率を計算することで、特徴量の重要性を高めることができます。この手法により、特定のカテゴリがターゲット変数に対して強い影響を持つかどうかを判断することが可能となり、特徴量エンジニアリングの段階でモデルの性能を向上させるために有用です。また、WOEは通常のカテゴリ変数のエンコーディング方法(例えば、One-Hotエンコーディング)に比べて、特徴量の次元を増加させないという利点も持っています。
ロジスティック回帰とは?
ロジスティック回帰の概要
ロジスティック回帰は、目的変数が二値(0か1)を取る分類問題に使われる代表的な統計モデルです。モデルの出力は0から1の間の確率を表し、この確率をもとにクラスを判定します。特徴量と目的変数の関係をモデル化するため、線形関係を仮定しており、特に解釈性が高いという特長があります。
ロジスティック関数
ここで、
P(y=1∣x) : y=1 になる確率
z: 線形結合 z=w⋅x+b
w: 特徴量x に対応する重みベクトル
b: バイアス(切片)
WOE変換とロジスティック回帰の関係
WOE変換は、カテゴリ変数をロジスティック回帰モデルで直接使用できるよう数値化する役割を果たします。これにより、モデルのパフォーマンスを向上させることができます。また、WOE変換はアウトライアに対して強い耐性を持つことから、ロジスティック回帰に適しています。
WOE変換を使った特徴量エンジニアリング
カテゴリ変数を扱うための方法
カテゴリ変数を扱うには、One-Hotエンコーディングやターゲットエンコーディングなどの手法がありますが、WOE変換はターゲット変数との関係性をうまく捉え、モデルにとって意味のある数値へと変換します。このように、WOE変換はカテゴリ変数の情報を効果的に取り入れるための優れた方法です。
WOE変換の手順
WOE変換の手順は以下の通りです:
- 最適なビン数の決定
WOEを計算する際には、連続変数をいくつのビン(区間)に分けるかを決定する必要があります。最適なビン数を決めるためには、以下の方法が一般的に用いられます:
・カッパ統計量:カテゴリ間の差異を測る指標であり、値が大きいほどカテゴリ分けが適切であると評価されます。
・決定木アルゴリズム:決定木ベースのアルゴリズム(例: CART)を使って、ターゲット変数との情報量(Information Gain)を最大化する分割点を見つけることができます。
・等間隔:等間隔に分割します。 - 各カテゴリに対して良いラベルの比率と、悪いラベルの比率を計算。
P(Good|Category): 特定のカテゴリにおいて、良いラベルの確率
P(Bad|Category): 特定のカテゴリにおいて、悪いラベルの確率 - その比率に基づいて、各カテゴリに対して「証拠の重み(Weight of Evidence)」を計算。
WOE = ln(P(Good|Category) / P(Bad|Category))
実行環境の準備
Google Colabの利用
Google Colabは、Pythonのコードをブラウザ上で簡単に実行できるクラウドサービスです。Pythonの実行環境が手元にない場合には特におすすめです。無料プランと有料プラン(Colab Pro)があり、有料プランではより長いセッション時間や高速なGPUを利用することができます。ただし、今回の実装ではGPUは不要であるため、無料プランで十分に対応可能です。Colabの利用方法は、このページに詳しく記載していますので、ご参照ください。
データセットの準備 – Breast Cancer Dataset
Breast Cancer Datasetの概要
データ分析や機械学習のためのPythonライブラリ「scikit-learn」には、各種サンプルデータが格納されています。その中の Breast Cancer Datasetは、乳がんの診断に関するデータセットで、特徴量に基づいてがんが良性か悪性かを分類するために使用されます。このデータセットには腫瘍の特徴(半径、テクスチャ、周長など)と、ターゲット変数である診断結果(良性または悪性)が含まれています。
データの読み込み方法と特徴量の説明
Breast Cancer Datasetのカラム一覧
以下にBreast Cancer Datasetの全てのカラムとその意味を一覧にまとめます。
カラム名 | 意味 |
---|---|
mean radius | 腫瘍の平均半径 |
mean texture | 腫瘍の平均テクスチャ(表面の質感) |
mean perimeter | 腫瘍の平均周長 |
mean area | 腫瘍の平均面積 |
mean smoothness | 腫瘍の平均平滑度(輪郭の滑らかさ) |
mean compactness | 腫瘍の平均コンパクト度(形の緊密さ) |
mean concavity | 腫瘍の平均凹度(凹んでいる部分の程度) |
mean concave points | 腫瘍の平均凹点数(凹んでいる部分の数) |
mean symmetry | 腫瘍の平均対称性 |
mean fractal dimension | 腫瘍の平均フラクタル次元(複雑さの指標) |
radius error | 半径の標準誤差 |
texture error | テクスチャの標準誤差 |
perimeter error | 周長の標準誤差 |
area error | 面積の標準誤差 |
smoothness error | 平滑度の標準誤差 |
compactness error | コンパクト度の標準誤差 |
concavity error | 凹度の標準誤差 |
concave points error | 凹点数の標準誤差 |
symmetry error | 対称性の標準誤差 |
fractal dimension error | フラクタル次元の標準誤差 |
worst radius | 最大の半径 |
worst texture | 最大のテクスチャ |
worst perimeter | 最大の周長 |
worst area | 最大の面積 |
worst smoothness | 最大の平滑度 |
worst compactness | 最大のコンパクト度 |
worst concavity | 最大の凹度 |
worst concave points | 最大の凹点数 |
worst symmetry | 最大の対称性 |
worst fractal dimension | 最大のフラクタル次元 |
Pythonのscikit-learnライブラリを使用することで、このデータセットを簡単に読み込むことができます。各特徴量には、腫瘍の半径(mean radius)、テクスチャ(mean texture)、周長(mean perimeter)などがあり、これらの特徴量ががんの診断にどのように影響するかを分析します。データセットの詳細についてはこちらをご覧ください。
Pythonを使った実装例
必要なライブラリのインストールとインポート
PythonでWOE変換とロジスティック回帰を行うためには、以下のライブラリをインストールします。
!pip install pandas numpy scikit-learn
次に、必要なライブラリをインポートします。
import pandas as pd
import numpy as np
from sklearn.linear_model import LogisticRegression
from sklearn.model_selection import train_test_split
from sklearn.metrics import accuracy_score, roc_auc_score
Breast Cancer Datasetの読み込みと確認
データセットを読み込み、目的変数と特徴量を確認します。
from sklearn.datasets import load_breast_cancer
data = load_breast_cancer()
df = pd.DataFrame(data.data, columns=data.feature_names)
df['TARGET'] = data.target
display(df)
target | mean radius | mean texture | mean perimeter | … | worst concavity | worst concave points | worst symmetry | worst fractal dimension | |
---|---|---|---|---|---|---|---|---|---|
0 | 0 | 17.99 | 10.38 | 122.80 | … | 0.71 | 0.27 | 0.46 | 0.12 |
1 | 0 | 20.57 | 17.77 | 132.90 | … | 0.24 | 0.19 | 0.28 | 0.09 |
2 | 0 | 19.69 | 21.25 | 130.00 | … | 0.45 | 0.24 | 0.36 | 0.09 |
3 | 0 | 11.42 | 20.38 | 77.58 | … | 0.69 | 0.26 | 0.66 | 0.17 |
… | … | … | … | … | … | … | … | … | … |
565 | 0 | 20.13 | 28.25 | 131.20 | … | 0.32 | 0.16 | 0.26 | 0.07 |
566 | 0 | 16.60 | 28.08 | 108.30 | … | 0.34 | 0.14 | 0.22 | 0.08 |
567 | 0 | 20.60 | 29.33 | 140.10 | … | 0.94 | 0.27 | 0.41 | 0.12 |
568 | 1 | 7.76 | 24.54 | 47.92 | … | 0.00 | 0.00 | 0.29 | 0.07 |
569 rows × 31 columns
このデータセットの説明変数は、全て連続値変数で、カテゴリ変数はなかったようです。
次にtargetの0と1の意味を確認してみます。
print(data_breast_cancer.target_names)
#['malignant' 'benign']
print(df.groupby('target')['target'].count())
#target
#0 212
#1 357
ターゲットのカテゴリ0と1の名前は、次のようになっていました。
0 = malignant:悪性、1 = benign:良性
また、ターゲットの件数を確認すると、0(malignant)も1(benign)も十分入っている事がわかりました。
malignant(悪性)とbenign(良性)の件数を色分けしてグラフ化し、データの分布を確認します。
fig, axes = plt.subplots(8, 4, figsize=(20,20))
# targetによるデータフレームのソート
malignant = df[df["target"] == 0]
benign = df[df["target"] == 1]
ax = axes.ravel()
fig.delaxes(ax[31]) # figから不要なaxを削除。
# 説明変数30個とtarget1個で、合計31個のグラフを作成する
for i in range(31):
_, bins = np.histogram(df.iloc[:,i], bins=20)
ax[i].hist(malignant.iloc[:,i].values, bins=bins, color='red', alpha=0.5)
ax[i].hist( benign.iloc[:,i].values, bins=bins, color='blue', alpha=0.5)
ax[i].set_title(df.columns[i])
ax[i].set_yticks(())
ax[0].set_xlabel("Feature Magnitude")
ax[0].set_ylabel("Frequency")
ax[0].legend(["malignant", "benign"], loc="best")
fig.tight_layout()
mean radiusなど、malignant(悪性, 赤色)とbenign(良性, 青色)のグラフの重ならない特徴量(説明変数)ほど、malignant(悪性)とbegning(良性)の分類に貢献してくれると期待できます。
WOE変換のライブラリ
今回はPythonライブラリのCategory Encodersを使用します。
!pip install category_encoders
ロジスティック回帰モデルの構築と訓練
WOE変換後のデータを使用して、ロジスティック回帰モデルを構築します。
import pandas as pd
import numpy as np
from sklearn.datasets import load_breast_cancer
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LogisticRegression
from sklearn.preprocessing import StandardScaler
from sklearn.metrics import accuracy_score, classification_report
from sklearn.pipeline import Pipeline
import category_encoders as ce
def compare_logistic_regression_with_woe(data):
X = pd.DataFrame(data.data, columns=data.feature_names)
y = pd.Series(data.target)
# データの分割
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)
# モデル1: 標準スケーリングのみ
pipe_standard = Pipeline([
('scaler', StandardScaler()),
('classifier', LogisticRegression(random_state=42))
])
# モデル2: WoE変換 + 標準スケーリング
pipe_woe = Pipeline([
('woe', ce.WOEEncoder()),
('scaler', StandardScaler()),
('classifier', LogisticRegression(random_state=42))
])
# モデルのトレーニングと評価
print("モデル比較: Breast Cancer Dataset\n")
# 標準スケーリングモデル
pipe_standard.fit(X_train, y_train)
y_pred_standard = pipe_standard.predict(X_test)
accuracy_standard = accuracy_score(y_test, y_pred_standard)
print("標準スケーリングモデル:")
print(f"精度: {accuracy_standard:.4f}")
print("分類レポート:")
print(classification_report(y_test, y_pred_standard))
# WoE変換モデル
pipe_woe.fit(X_train, y_train)
y_pred_woe = pipe_woe.predict(X_test)
accuracy_woe = accuracy_score(y_test, y_pred_woe)
print("\nWoE変換モデル:")
print(f"精度: {accuracy_woe:.4f}")
print("分類レポート:")
print(classification_report(y_test, y_pred_woe))
# 精度改善の確認
print(f"\n精度の差: {accuracy_woe - accuracy_standard:.4f}")
if __name__ == "__main__":
# Breast Cancer Datasetの読み込み
data = load_breast_cancer()
compare_logistic_regression_with_woe(data)
今回のColabで実行した結果は次のようになりました。
デル比較: Breast Cancer Dataset
標準スケーリングモデル:
精度: 0.9737
分類レポート:
precision recall f1-score support
0 0.98 0.95 0.96 43
1 0.97 0.99 0.98 71
accuracy 0.97 114
macro avg 0.97 0.97 0.97 114
weighted avg 0.97 0.97 0.97 114
Warning: No categorical columns found. Calling 'transform' will only return input data.
WoE変換モデル:
精度: 0.9737
分類レポート:
precision recall f1-score support
0 0.98 0.95 0.96 43
1 0.97 0.99 0.98 71
accuracy 0.97 114
macro avg 0.97 0.97 0.97 114
weighted avg 0.97 0.97 0.97 114
精度の差: 0.0000
標準のロジスティック回帰モデルと、WoE変換したモデルで、精度の差はありませんでした。これはデータの説明変数が、WoEの恩恵を得られるほど複雑な分布をしていなかった為と思われます。
8. まとめ
WOE変換のメリットとデメリット
WOE変換のメリットは、カテゴリ変数の情報を効果的に取り入れられることや、解釈性が高いことです。一方、計算コストがかかる点や、大量のカテゴリを持つ変数に対しては非効率になる場合があることがデメリットです。
実務における機械学習への適用例と注意点
WOE変換は金融業界などでよく使われており、信用スコアリングなどに活用されています。しかしWOE変換は過学習に陥りやすい傾向があります。WOE変換は、各ビン(区間)内のターゲット変数(通常は0または1)の比率を用いて特徴量を変換しますので、ターゲットに強く依存する特徴量となり、モデルがトレーニングデータに対して過剰にフィットする為です。これを避けるためには慎重なチューニングとテストが必要です。
9. 参考文献・リンク集
WOE変換に関する参考文献
- 「The Weight of Evidence: Its Strength and Its Weakness」
ロジスティック回帰に関する追加学習リソース
- scikit-learnの公式ドキュメント: Logistic Regression