ブースティングの解釈 — 500 本の木が語る変数の声

ESL 10.13 Interpretation

XGBoost や LightGBM で学習させた直後、最初に開かれるのが feature_importances_ のグラフだ。 「年齢が一番効いている」「収入もそこそこ」「曜日はほぼ効かない」 ——棒グラフはモデルの中身を語ってくれる。

しかし、ここで足を止めたい。500 本の決定木を足し合わせた予測器、その内部はもはや一本の木のような 「if-then の連鎖」ではない。それなのに、なぜ「変数 X は重要度 30」などと一つの数字で要約できるのだろう? そして「年齢が増えると予測値はどう変わるのか?」に答える図 (Partial Dependence Plot) は、 その正しい解釈を意識して読んでいる人は意外と少ない。

キーワードは「勾配の総和」と 「周辺化」。 後者は「条件付き期待値」と取り違えると、まったく違う物語になる。それも見届けよう。

一本の木は読める。けれど 500 本は?

決定木が長らく愛されてきた理由のひとつは、そのまま図として描けることだった。 「年齢が 40 歳以上なら右、未満なら左」。各分岐に意味があり、葉に予測値が書かれ、 上から下までたどれば判断の理由が説明できる。これほど解釈しやすい予測器は珍しい。

ところがブースティングは、この長所をあっさり手放す。 ブースティングとは「前の木の誤差を埋めるように、新しい木を順に足し算していく」手法だ。 1 本目は普通に学習する。2 本目は 1 本目が外したところを重点的に当てに行く。 3 本目は 1 + 2 本目の合計でまだ外しているところを担当する……というふうに、 $M$ 本の木がそれぞれ違う役割を持って積み上がる。

一本の読める決定木から500本の読めない集合体へ変化し最終予測に集約される
左: 読める一本の木。右: 読めない集合体。中央下で全予測が合算される。

結果としてモデルは

$$f(x) = \sum_{m=1}^{M} T_m(x)$$

という、$M$ 本の木の足し算になる。$M$ は数百から数千。 1 本ずつ眺めても、全体としてモデルが何を学んだのかは見えない。「説明できる予測器」が「説明できない予測器」になる——これがブースティングの代償だ。

ではどうするか。ESL 10.13 が提案するのは、見方を切り替えるという大人な戦略だ。 モデルの「中身」を全部見るのではなく、モデルが「どの変数に注目していたか」と、「ある変数を動かすと予測がどう変わるか」を聞く。 これだけでも、ブラックボックスの輪郭はかなりはっきり浮かび上がってくる。

木の中で「働いた量」を測る — 変数重要度

最初の技は、変数重要度 (Relative Importance) だ。 発想は驚くほど素朴で、「この変数が分割に使われたとき、誤差をどれだけ減らせたか」を集めて足す、それだけ。

まずは一本の木で考える

一本の木 $T$ には、内部ノード(分岐点)が $J-1$ 個ある (葉は $J$ 個。二分木では「葉の数 − 1 = 分岐点の数」になる)。 各内部ノード $t$ では、ある変数 $X_v(t)$ が選ばれて、その点でデータが二つに割られる。 ここで $v(t)$ は「ノード $t$ で分割に使われた変数の番号を返す関数」と思えばよい。

このとき、「割られた結果、二乗誤差がどれだけ縮まったか」を 改善量 $i^2_t$ と書く。分割する前、ノード $t$ にあるデータ全部を一つの予測値(平均)で予測していた。 そのときの誤差を測る。次に、分割した後の左の子と右の子で、それぞれ別の予測値(やはり平均)を使う。 「分割前の誤差 − 分割後の誤差」がプラスになっていれば、その分だけ二乗誤差が減った ——その減少分が改善量だ。

木のノードごとに改善量が測られ、変数別に積算されて棒グラフが伸びていく
各ノードの改善量が変数ごとに集計され、重要度ランキングが完成する。

変数 $X_\ell$ の重要度を、そのノードで $X_\ell$ が分割変数として選ばれていたなら改善量を加算する形で定義する:

$$\mathcal{I}_\ell^2(T) = \sum_{t=1}^{J-1} i^2_t \cdot \mathbf{1}[v(t) = \ell]$$

式の中の指示関数 $\mathbf 1[\cdot]$ は、中身が真なら 1、偽なら 0 を返す。 変数 $X_\ell$ が一度も選ばれなければ重要度はゼロ、いろんなノードで選ばれて毎回大きく誤差を 減らしていれば重要度は大きくなる。シンプルだが、まっとうな尺度だ。

ブースティングではどうするか

ブースティングは木 $T_1, T_2, \ldots, T_M$ を順に作るので、それぞれの木で重要度を計算して、平均を取るのが自然な拡張だ:

$$\mathcal{I}_\ell^2 = \frac{1}{M} \sum_{m=1}^{M} \mathcal{I}_\ell^2(T_m)$$

一本の木はちょっとの偶然で「たまたまこの変数を使った」と揺らぐが、$M$ 本も平均すれば 偶然は均され、より安定した重要度が得られる。

実務でよく見る棒グラフは、重要度の平方根を、 最大値が 100 になるように正規化したものだ。「重要度」と呼ぶときは、二乗のまま使っているのか、 平方根を取っているのか、頭の片隅に置いておくと混乱が減る。

「他の変数の声」を消して、ひとつだけ聞く — 部分依存

変数重要度は「どの変数が効いているか」のランキングを教えてくれる。 だが、それだけでは足りない。次に知りたいのは「その変数を動かすと、予測値はどう変わるのか」だ。

たとえば、住宅価格の予測モデルで、「住宅の平均部屋数」が重要だと分かったとする。 では、平均部屋数が 3 から 8 へ動くとき、価格予測は単調に上がるのか、ある点で頭打ちになるのか、 それともU字を描くのか? ——これに答えるのが部分依存プロット(Partial Dependence Plot, PDP) だ。

部分依存の定義

入力変数を二つのグループに分ける。注目したい少数の変数 $X_S$(例: 平均部屋数だけ)と、 それ以外の全部 $X_C$ だ。記号の由来は $S$ が subset(注目するグループ)、$C$ が complement(残り)の頭文字。

モデル全体 $f(X)$ は両方に依存しているけれど、$X_C$ について平均してしまえば、$X_S$ だけの関数になる:

$$f_S(X_S) = \mathbb{E}_{X_C}\!\left[\,f(X_S, X_C)\,\right]$$

これが部分依存だ。「$X_C$ をすべての可能な値で平均化したときの、$X_S$ だけが効いた効果」。 $X_C$ をぐるりと回して、その平均的な振る舞いを見ているわけだ。

数値的にはどう計算するか

理論的な期待値は計算できないので、訓練データの $X_C$ の値 $x_{1C}, \ldots, x_{NC}$ を使ったモンテカルロ近似で済ませる:

$$\hat{f}_S(X_S) = \frac{1}{N} \sum_{i=1}^{N} f(X_S, x_{iC})$$

これは要するに、「$X_S$ の値を固定して、$X_C$ の部分を訓練データから丸ごと持ってきて、 $N$ 回モデルを評価して平均する」という作業だ。 $X_S$ を細かいグリッドで動かしながら同じ計算を繰り返せば、部分依存 $\hat f_S$ の曲線が描ける。 $X_S$ が一変数なら線、二変数なら等高線図やヒートマップになる。

個別の予測曲線(N本)が平均化されて部分依存の太い黄色い曲線が浮かび上がる
左: N人分の個別曲線(各々の X_C の値で描いた予測)。右: それらの平均 = 部分依存曲線(黄)。

アニメーションで見えるように、20 本の半透明な青い曲線がそれぞれ異なる $X_C$ の値に対応している。 これらの「声」を全部重ねて平均したものが、右側の太い黄色い曲線 —— つまり$X_S$ の純粋な効果だ。

PDP に潜む罠 — 周辺化と条件付きはまったく別物

ここで一つ、罠を共有しておきたい。部分依存とよく似ているが全く違う量がある。 それが条件付き期待値だ:

$$\tilde{f}_S(X_S) = \mathbb{E}\!\left[\,f(X_S, X_C)\,\mid\, X_S\,\right]$$

両者の違いを文章で言うと:

数式で見ると微妙な差だが、これが解釈に与える影響は大きい。 たとえば、$X_S$ がモデル $f$ に全く効いていないとしよう。それでも $X_S$ と $X_C$ に 強い相関があれば、$X_S$ が動くと $X_C$ の分布も動き、条件付き期待値は値を変えてしまう。 「$X_S$ は重要に見える」が、実際にモデルが $X_S$ をどう使っているかは何も教えてくれない。

X_SとX_Cに相関があるとき、周辺化(黄・平坦)と条件付き(赤・右上がり)が全く違う曲線を返す
上: X_S と X_C に正の相関がある散布図。下左: 部分依存(黄、平坦)。下右: 条件付き期待値(赤、右上がり)。

部分依存はここで賢く立ち回る。$X_C$ を訓練データ全体から平均することで、 $X_S$ と $X_C$ の関係に引きずられない、「$X_C$ の効果を取り除いた後の $X_S$ の効果」を抽出する。

加法分解との関係

もし $f$ が二つの変数群について加法的だったら、つまり

$$f(X) = h_1(X_S) + h_2(X_C)$$

の形をしていれば、部分依存 $f_S(X_S)$ は(加法定数の違いを除いて)ちょうど $h_1(X_S)$ を取り出す。 条件付き期待値ではこのきれいな性質は得られない。

部分依存は「モデルの中での $X_S$ の純粋な役割」を見ようとしている——この一文を覚えておけば、PDPの読み方に迷うことはない。

多クラスでは「クラスごとの声」を聞く

最後に、二値分類や回帰だけでなく、多クラス分類でも同じ二つの技が使えることを見ておこう。

$K$ クラス分類のブースティングは、各クラスごとに一本ずつ加法モデル $f_k(x)$ を作る:

$$f_k(x) = \sum_{m=1}^{M} T_{km}(x), \quad k = 1, 2, \ldots, K$$

そして softmax で確率に変換する。このとき $f_k(x)$ は対数オッズ風のスケールで動く:

$$f_k(X) = \log p_k(X) - \frac{1}{K} \sum_{j=1}^{K} \log p_j(X)$$

式の読み方は「クラス $k$ の確率の対数(左の項)から、全クラスの対数確率の平均(右の項)を引いた量」。 $f_k(X)$ は「クラス $k$ が平均よりどれだけ確率的に上か下か」を表す数値だ。 $f_k = 0$ ならクラス $k$ は他のクラスと並、$f_k > 0$ なら平均より優勢$f_k < 0$ なら劣勢、と読める。

クラス別の変数重要度

クラス $k$ にとっての $X_\ell$ の重要度は、クラス $k$ の木だけで集計すればよい:

$$\mathcal{I}_{\ell k}^2 = \frac{1}{M} \sum_{m=1}^{M} \mathcal{I}_\ell^2(T_{km})$$

これは「$X_\ell$ が、他のクラスからクラス $k$ を切り分けるのにどれだけ役立ったか」を測る。 クラスごとに違う棒グラフが出るので、「年齢は若年層クラスでは強いが、高齢層クラスでは弱い」といったクラス依存のストーリーが読み取れる。

3クラスの変数重要度棒グラフが出現し、矢印で平均化されて全体重要度グラフが完成する
上: クラスA(赤)・B(緑)・C(青)それぞれの重要度。下: 3クラスを平均した全体重要度(黄)。

全クラスを通した重要度が欲しければ、$K$ クラスで平均する:

$$\mathcal{I}_\ell^2 = \frac{1}{K} \sum_{k=1}^{K} \mathcal{I}_{\ell k}^2$$

クラス別の部分依存

部分依存も同じで、各 $f_k$ について別々に作る。 「変数 $X_S$ を動かすと、クラス $k$ のロジットがどう変わるか」が読める。 Section 3 の図がクラスの数だけ並ぶ、と想像すればよい。

softmax を通せば確率になるが、プロットは普通ロジットのままで読む。 なぜなら、softmax を通すと変数の効果がクラス間で混ざるので、解釈が難しくなるからだ。

ここまでの二つの技 ——変数重要度部分依存プロット—— を組み合わせれば、ブースティングが「ブラックボックス」と呼ばれていたのが不思議になるくらい、 モデルの中身に光が差してくる。完全に透明ではない。だが、主役を見つけ、その振る舞いを描き出すことは、 こんなにシンプルな道具立てでできてしまう。

まとめ

ブースティングは、解釈性を捨てる代わりに精度を取った手法だ。 だが、ESL 10.13 が示すように、捨てたはずの解釈性を横道から取り戻すことはできる。

これらは XGBoost や LightGBM などのライブラリで標準装備されているが、 その裏側の数式を知っていると、出てきた図の「読み方」が違ってくる。

ブラックボックスは、覗き方を知れば、多くの場合グレーボックスくらいまでは透ける