🎓 レベル:発展 | 重要度:B(標準)
📎 前提:バックドア基準と識別 | 識別の仮定 | 逆確率重み付けIPW
要点(BLUF)
- AIPW(拡張IPW) は回帰調整(アウトカムモデル )とIPW(傾向スコア )を組み合わせた推定量。
- 二重頑健性 (doubly robust):アウトカムモデルと傾向スコアモデルのどちらか一方が正しければ、AIPW は ATE の一致推定量になる。正しいモデルを当てる機会が2回ある。
- 回帰単独・IPW単独は自分のモデルが誤ると外すが、AIPW は片方が誤ってももう片方が救う。これを2つの誤特定状況で数値実証する。ただし両方とも誤れば AIPW も外す。
1. 概念:2つの推定量を「補正項」で繋ぐ
これまで交絡を消す道具を2つ見た。
- 回帰による調整とその限界:アウトカムモデル を当て、 とする。結果の関数形が正しい必要がある。
- 逆確率重み付けIPW:傾向スコア の逆数で重み付けする。処置の確率モデルが正しい必要がある。
AIPW は両者を融合する。 の推定量は
第1項は回帰予測そのもの。第2項は残差 を IPW で重み付けした補正項。 も対称に定義し、。
flowchart TB
O["アウトカムモデル m(C) が正しい"] --> A["AIPW 推定量"]
P["傾向スコア e(C) が正しい"] --> A
A --> R["どちらか一方が正しければ ATE に一致(二重頑健)"]
2. 識別:なぜ二重頑健になるか(導出)
を真のアウトカム回帰、 を真の傾向スコアとし、推定値 は誤っているかもしれないとする。AIPW の被加算項を で条件づけて期待値を取る。交換可能性 より 、 なので、
右辺を 中心に整理すると、
第2項がバイアス項である。これが消える条件は2通り。
- 傾向スコアが正しい():すると となり、 がどんなに間違っていても第2項は消える。
- アウトカムモデルが正しい():すると で、 がどんなに間違っていても第2項は消える。
どちらか一方が成り立てば 条件付き期待値が真の に一致し、外側で平均すれば になる。これが二重頑健性の正体だ。積 は2つの誤差の掛け算なので、片方がゼロなら全体がゼロになる――この構造が鍵である。
❓ 確認:二重頑健は「両方間違っていてもよい」という意味だろうか? 違う。少なくとも片方は正しいことが要る。両方の誤差が残ると、その積がバイアスとして残る(後述の (d))。
3. 実証:片方が誤っても AIPW は当てる
真の傾向スコアとアウトカムがどちらも交互作用(非線形)を含むデータを作る()。「正しいモデル」は交互作用込み、「誤特定モデル」は線形のみ、として切り替える。回帰調整・IPW・AIPW を4つの状況で比較する。
import warnings
import numpy as np
from sklearn.linear_model import LogisticRegression, LinearRegression
warnings.filterwarnings("ignore")
# === 二重頑健: アウトカムか傾向スコアの片方が誤っても AIPW は ATE を当てる ===
def make_data(seed):
rng = np.random.default_rng(seed)
n = 8000
X1 = rng.normal(0, 1, size=n)
X2 = rng.normal(0, 1, size=n)
# 真の傾向スコア・アウトカムはどちらも交互作用(非線形)を含む
logit_true = 0.7 * X1 + 0.7 * X2 + 0.6 * X1 * X2
e_true = 1.0 / (1.0 + np.exp(-logit_true))
T = rng.binomial(1, e_true)
ATE_true = 2.0
baseline = 1.0 + 2.0 * X1 + 2.0 * X2 + 2.0 * X1 * X2
Y = baseline + ATE_true * T + rng.normal(0, 1, size=n)
return X1, X2, T, Y
def features(X1, X2, correct):
# correct=True: 交互作用込み(正しい)。False: 線形のみ(誤特定)
if correct:
return np.column_stack([X1, X2, X1 * X2])
return np.column_stack([X1, X2])
def estimate(seed, outcome_correct, ps_correct):
X1, X2, T, Y = make_data(seed)
Z_out = features(X1, X2, outcome_correct)
Z_ps = features(X1, X2, ps_correct)
# アウトカムモデル(処置群・対照群で別々に回帰し標準化)
mu1 = LinearRegression().fit(Z_out[T == 1], Y[T == 1]).predict(Z_out)
mu0 = LinearRegression().fit(Z_out[T == 0], Y[T == 0]).predict(Z_out)
reg = (mu1 - mu0).mean()
# 傾向スコアモデル
e = LogisticRegression(max_iter=1000).fit(Z_ps, T).predict_proba(Z_ps)[:, 1]
e = np.clip(e, 0.01, 0.99)
# 安定化(Hajek)IPW
w1, w0 = T / e, (1 - T) / (1 - e)
ipw = (w1 * Y).sum() / w1.sum() - (w0 * Y).sum() / w0.sum()
# AIPW(二重頑健): 回帰予測 + IPW による残差補正
psi1 = mu1 + T * (Y - mu1) / e
psi0 = mu0 + (1 - T) * (Y - mu0) / (1 - e)
aipw = (psi1 - psi0).mean()
return reg, ipw, aipw
def summarize(label, outcome_correct, ps_correct):
results = np.array([estimate(s, outcome_correct, ps_correct) for s in range(100)])
reg, ipw, aipw = results.mean(axis=0)
print(f"{label}")
print(f" 回帰調整 {reg:5.3f} | IPW {ipw:5.3f} | AIPW {aipw:5.3f}")
print("真の ATE = 2.000 (100回反復の平均)\n")
summarize("(a) アウトカム誤特定・傾向スコア正しい:", outcome_correct=False, ps_correct=True)
summarize("(b) 傾向スコア誤特定・アウトカム正しい:", outcome_correct=True, ps_correct=False)
summarize("(c) 両方とも正しい :", outcome_correct=True, ps_correct=True)
summarize("(d) 両方とも誤特定 :", outcome_correct=False, ps_correct=False)
実行結果は次の通り。
真の ATE = 2.000 (100回反復の平均)
(a) アウトカム誤特定・傾向スコア正しい:
回帰調整 2.910 | IPW 2.036 | AIPW 2.023
(b) 傾向スコア誤特定・アウトカム正しい:
回帰調整 1.997 | IPW 2.964 | AIPW 1.996
(c) 両方とも正しい :
回帰調整 1.997 | IPW 2.036 | AIPW 1.997
(d) 両方とも誤特定 :
回帰調整 2.910 | IPW 2.964 | AIPW 3.317
出力の意味――ここが二重頑健の核心だ。
- (a) アウトカムだけ誤特定:回帰調整は 2.910 と大きく外す(線形で交互作用を見落とす)。だが傾向スコアが正しいので、IPW は 2.036、AIPW も 2.023 と真値を当てる。
- (b) 傾向スコアだけ誤特定:今度は IPW が 2.964 と外す。だがアウトカムモデルが正しいので、回帰調整は 1.997、AIPW も 1.996 と当てる。
- (c) 両方正しい:当然どれも 2.0 付近。
- (d) 両方誤特定:回帰も IPW も外し、AIPW も 3.317 と外す。二重頑健は「どちらか片方は正しい」が前提で、両方崩れれば救えない。
(a) と (b) を見比べてほしい。回帰調整は (a) で外し、IPW は (b) で外すのに、AIPW だけが (a) でも (b) でも真値を当てている。片方のモデルが誤ってももう片方が補正する――これが「2回チャンスがある」推定量の威力だ。
4. なぜ強力なのか/何が限界か(直観)
二重頑健性のうれしさは、モデル選択の失敗に対する保険である。観察データでは、結果の関数形も処置の確率も真の形は分からない。AIPW なら「2つのモデルのうち少なくとも1つを当てればよい」ので、当てる確率が上がる。
数理的には、バイアスが2つの誤差の積 になることが効いている。各モデルの誤差が小さければ、その積はさらに小さい(二次のバイアス)。この性質は、 と を機械学習で柔軟に推定したい場合に決定的になる。MLは単体では正則化バイアスを持ち込むが(MLをそのまま使うと因果を誤る理由)、AIPW 型の補正とクロスフィッティングを組み合わせると、そのバイアスが二次に抑えられる。これを定式化したのがDouble/Debiased Machine Learning(DML)であり、AIPW はその古典的な原型にあたる。
限界は明確だ。(d) が示すように、両方のモデルが誤れば二重頑健性は無力。また AIPW は IPW を内包するため、正値性が崩れれば同じく分散が膨らむ。二重頑健は「関数形の誤特定」への保険であって、未観測交絡や正値性違反(識別の仮定)を救うものではない。
⚠️ よくある誤解・落とし穴
- 「二重頑健=何があっても正しい」ではない。守ってくれるのは関数形の誤特定に対してだけ。識別の仮定(交換可能性・正値性・SUTVA)が崩れていれば、回帰も IPW も AIPW も等しく誤る。
- 両方少しずつ誤っている現実:実務では両モデルとも完璧ではない。それでも誤差の積がバイアスなので、各々がそこそこ良ければ AIPW のバイアスは小さい――これが「弱い意味の二重頑健」の御利益。
- MLで を推定するなら素のAIPWでは過学習バイアスが乗る。同じデータで学習と評価をすると残差補正が効かない。クロスフィッティング(交差検証の発想で標本を分割)が必須で、これがDouble/Debiased Machine Learning(DML)の中心テーマ。
- 正値性の確認を怠らない。AIPW でも の極端値(0/1近傍)は補正項を爆発させる。重なり診断は IPW と同様に必要。
関連ノート
- 因果:逆確率重み付けIPW(補正項の素となるIPW)/回帰による調整とその限界(アウトカムモデル側)/傾向スコア(傾向スコア側)/MLをそのまま使うと因果を誤る理由(MLの正則化バイアス)/Double/Debiased Machine Learning(DML)(AIPW+クロスフィッティングの一般化)/識別の仮定(二重頑健でも救えない仮定)
- 機械学習:訓練・検証・テストと交差検証(クロスフィッティングの基礎)/正則化(Ridge・Lasso・Elastic Net)(柔軟な学習器の正則化バイアス)