시리즈의 마지막 편이고 두 갈래가 만나는 곳입니다.
This is the last post in the series, and it is where the two halves meet.
인과추론 섹션은 계수 하나를 제대로 추정하는 이야기였습니다. 머신러닝 섹션은 고전적 방법이 감당할 수 있는 것보다 변수가 많을 때를 다뤘습니다. Double LASSO는 두 문제가 동시에 있을 때 쓰는 것입니다. 인과 질문이 있고 통제변수 후보가 백 개 있고 어느 것이 중요한지 강한 이론이 없을 때.
The Causal Inference section was about estimating one coefficient correctly. The Machine Learning section was about handling more variables than classical methods can absorb. Double LASSO is what you use when you have both problems at once: a causal question, a hundred potential controls, and no strong theory about which ones matter.
자명한 접근이 실패하는 이유Why the obvious approach fails
자연스러운 본능은 LASSO에게 통제변수를 고르게 하는 것입니다. 결과를 처치와 모든 후보 통제변수에 LASSO 회귀하고 살아남은 것을 남긴 다음, 선택된 집합으로 OLS를 돌려 처치 계수와 표준오차를 보고합니다.
The natural instinct is to let LASSO choose the controls: run LASSO of the outcome on treatment and all candidate controls, keep whatever survives, then run OLS on the selected set and report the treatment coefficient with its standard error.
작동하지 않습니다. 실패는 작은 왜곡이 아닙니다. 결과 신뢰구간이 심하게 미달 포함합니다. 명목 95% 구간이 참값을 훨씬 덜 자주 담고 추정치는 부호를 알 수 없는 방향으로 편향됩니다.
This does not work, and the failure is not a small distortion. The resulting confidence intervals under-cover badly — nominal 95% intervals can contain the truth far less often — and the estimate is biased in a direction you cannot sign.
기제가 둘입니다.
Two mechanisms are at work.
- 선택은 추론이 아닙니다. LASSO는 예측 오차를 최소화하려고 줄이고 고릅니다. 그 목적함수는 편향 없는 처치효과 복원과 아무 상관이 없습니다. 예측에 도움이 되는 축소가 관심 계수에 편향을 도입합니다.
- 2단계가 1단계가 있었다는 사실을 무시합니다. 선택된 변수로 OLS를 돌리고 그 표준오차를 보고하는 것은 선택 집합이 사전에 지정된 것처럼 취급합니다. 아니었습니다. 같은 데이터로 골랐습니다. 그러므로 표준오차는 틀린 절차를 기술합니다. 엿보기 편이 A/B 테스트에서 기술한 것과 정확히 같은 방식입니다.
- Selection is not inference. LASSO shrinks and selects to minimise prediction error. That objective has nothing to do with recovering an unbiased treatment effect, and the shrinkage that helps prediction introduces bias in the coefficient of interest.
- The second stage ignores that the first stage happened. Running OLS on the selected variables and reporting its standard errors treats the selected set as if it had been specified in advance. It was not — it was chosen using the same data. The standard errors therefore describe the wrong procedure, exactly as the peeking post described for A/B tests.
이중 선택 해법The double selection fix
Belloni, Chernozhukov, Hansen의 해법은 LASSO를 서로 다른 두 방정식에 두 번 돌리고 선택된 것의 합집합을 쓰는 것입니다.
Belloni, Chernozhukov and Hansen solution is to run LASSO twice, on two different equations, and take the union of what they select.
- 첫 번째 LASSO: 결과를 모든 후보 통제변수에 회귀합니다. 선택 집합을 보관합니다.
- 두 번째 LASSO: 처치를 모든 후보 통제변수에 회귀합니다. 그 선택 집합도 보관합니다.
- 최종: 결과를 처치와 두 선택 집합의 합집합에 OLS 회귀합니다.
- First LASSO: regress the outcome on all candidate controls. Keep the selected set.
- Second LASSO: regress the treatment on all candidate controls. Keep that selected set.
- Final step: run OLS of outcome on treatment plus the union of both selected sets.
합집합이 핵심입니다. 교란변수는 두 방정식 중 하나에서만 중요해도 남습니다. 이것이 위의 실패 양상을 직접 해결합니다. 처치를 강하게 예측하지만 결과는 약하게 예측하는 변수가 첫 LASSO에서 버려져도 두 번째가 잡아 냅니다.
The union is the whole point. A confounder needs only to matter for one of the two equations to be retained, which directly addresses the failure mode above. Variables that predict treatment strongly but the outcome weakly are caught by the second LASSO even when the first discards them.
import numpy as np
import statsmodels.api as sm
from sklearn.linear_model import LassoCV
rng = np.random.default_rng(12)
n, p, TRUE = 2_000, 200, 1.0
# a confounder that matters a lot for D and only weakly for Y - the trap
X = rng.normal(size=(n, p))
beta_y = np.zeros(p); beta_y[:5] = 1.0; beta_y[5] = 0.25
beta_d = np.zeros(p); beta_d[:5] = 1.0; beta_d[5] = 2.00
d = X @ beta_d + rng.normal(size=n)
y = TRUE * d + X @ beta_y + rng.normal(size=n)
def selected(target):
fit = LassoCV(cv=5, random_state=0).fit(X, target)
return set(np.flatnonzero(fit.coef_))
single = selected(y) # naive: outcome equation only
double = single | selected(d) # union of both equations
def effect(cols):
design = sm.add_constant(np.column_stack([d, X[:, sorted(cols)]]))
return sm.OLS(y, design).fit().params[1]
print(f"true effect : {TRUE:.4f}")
print(f"single LASSO : {effect(single):.4f} ({len(single)} controls)")
print(f"double selection : {effect(double):.4f} ({len(double)} controls)")
print(f"confounder 5 kept? single={5 in single} double={5 in double}")true effect : 1.0000
single LASSO : 1.0779 (6 controls)
double selection : 1.0032 (7 controls)
confounder 5 kept? single=False double=True
단일 LASSO는 문제의 교란변수를 버리고 8% 위로 편향됩니다. 이중 선택은 두 번째 방정식을 통해 그것을 잡고 참값을 되찾습니다. 통제변수 하나 차이입니다.
The single LASSO drops the offending confounder and comes out 8% high. Double selection catches it via the second equation and recovers the truth. The difference is one control variable.
결과는 일치성과 점근적 정규성을 갖는 처치효과 추정치입니다. 표준오차가 유효하므로 신뢰구간을 보고하고 그 말을 지킬 수 있습니다.
The result is an estimate of the treatment effect that is consistent and asymptotically normal, with standard errors that are valid — so you can report a confidence interval and mean it.
부분화 형식과 그 일반화The partialling-out formulation
밀접하게 관련된 부분화 또는 이중 머신러닝 형식이 논리를 더 분명하게 만듭니다. 결과를 통제변수에 회귀해 잔차를 얻고 처치도 통제변수에 회귀해 잔차를 얻은 다음, 한 잔차를 다른 잔차에 회귀합니다. Frisch–Waugh–Lovell 정리에서 잔차화를 머신러닝이 하는 것입니다. LASSO를 넘어 랜덤 포레스트·부스팅·신경망으로 일반화됩니다.
The closely related partialling-out or double machine learning formulation makes the logic clearer: residualise the outcome on the controls, residualise the treatment on the controls, then regress one residual on the other. This is the Frisch-Waugh-Lovell theorem with machine learning doing the residualisation, and it generalises beyond LASSO to random forests, boosting or neural networks.
그 일반화를 작동시키는 기술적 재료가 둘이고 이름으로 알아 둘 값어치가 있습니다.
Two technical ingredients make that generalisation work, and both are worth knowing by name.
- Neyman 직교성. 적률조건이 방해모수 추정의 작은 오차가 처치 추정치에 2차 효과만 갖도록 구성됩니다. 불완전한 1단계에 관용을 사 주는 것이 이것입니다.
- 교차적합. 방해함수를 데이터의 한 분할에서 추정해 다른 분할에 적용함으로써, 같은 관측치를 두 번 쓰는 데서 오는 과적합 편향을 제거합니다. 실무에서 이게 상당히 중요합니다. 이를 건너뛴 구현은 눈에 띄게 편향됩니다.
- Neyman orthogonality. The moment condition is constructed so that small errors in estimating the nuisance functions have only a second-order effect on the treatment estimate. This is what buys tolerance to imperfect first stages.
- Cross-fitting. Nuisance functions are estimated on one split of the data and applied to another, removing the overfitting bias that arises from using the same observations twice. In practice this matters a great deal, and implementations that skip it are noticeably biased.
무엇을 사고 무엇을 사지 못하는가What this does and does not buy you
달리 말하면, 이것은 모형 선택 문제를 풀지 식별 문제를 풀지 않습니다. IV나 RD가 아니라 매칭과 같은 범주에 속합니다.
Put differently: this solves a model selection problem, not an identification problem. It belongs in the same category as matching, not as IV or RD.
실무에서In practice
- 확립된 구현을 쓰십시오.
DoubleML(파이썬·R)과 Microsoft의EconML이 교차적합을 포함해 이중 머신러닝을 올바르게 구현합니다. 손으로 짜는 건 여기서처럼 좋은 연습이고 나쁜 운영 선택입니다. 유효하게 만드는 세부사항을 미묘하게 틀리기 쉽습니다. - 최종 회귀에 처치를 벌점 없이 넣으십시오. 처치 계수는 절대 축소되면 안 됩니다. 일부 구현은 이것을 명시적으로 지정하라고 요구합니다.
- 교차적합하십시오. 표본 분할 없이는 방해함수 추정이 과적합되고 처치 추정치가 그 편향을 물려받습니다. 5겹이 통상적 기본값입니다. 여러 무작위 분할에 걸쳐 반복해 평균 내면 특정 분할에 기대는 정도가 줄어듭니다.
- 균형과 중첩 확인을 건너뛰지 마십시오. 성향점수 편의 모든 내용이 여전히 적용됩니다. Double LASSO는 통제변수 선택을 원리적으로 만들지, 비교군이 존재하는지를 알려 주지 않습니다.
- 각 LASSO가 무엇을 골랐는지 보고하고 그 불안정성도 밝히십시오. 선택 집합은 부트스트랩 표본에 따라, 특히 상관된 통제변수에서 달라집니다. 예상된 일입니다. 이 방법이 보장하는 것은 처치효과이지 선택 집합이 아닙니다. 다만 독자가 변수 목록을 발견으로 믿게 두어서는 안 됩니다.
- 가정한 것에 대해 정직하십시오. 글에는 이렇게 써야 합니다. 교란변수가 이 후보 집합 안에 있다고 가정하고, 그중에서 이중 LASSO로 선택했다. 추정량의 정교함이 시사하는 것보다 훨씬 강한 주장이고 독자가 작업을 평가하려면 필요한 주장입니다.
- Use an established implementation.
DoubleML(Python and R) and MicrosoftEconMLboth implement double machine learning correctly, including cross-fitting. Hand-rolling it is a good exercise, as here, and a poor production choice — the details that make it valid are easy to get subtly wrong. - Always include treatment unpenalised in the final regression. The treatment coefficient must never be shrunk. Some implementations require you to say this explicitly.
- Cross-fit. Without sample splitting the nuisance estimates overfit and the treatment estimate inherits that bias. Five folds is the usual default, and repeating over several random splits and averaging reduces dependence on any one partition.
- Do not skip the balance and overlap checks. Everything from the propensity score posts still applies. Double LASSO makes control selection principled; it does not tell you whether a comparison group exists.
- Report which variables each LASSO selected, and note the instability. The selected set shifts across bootstrap samples, particularly with correlated controls. This is expected — the guarantees are about the treatment effect, not the selected set — but readers should not be led to believe the variable list is a finding.
- Be honest about what is assumed. The write-up should say: we assume the confounders lie within this candidate set, and we selected among them by double LASSO. That is a much stronger claim than the estimator sophistication might suggest, and it is the claim a reader needs in order to evaluate the work.
풍부한 상품·고객 속성이 있는데 어느 것이 교란하는지 이론이 특정하지 않는 가격·수요 추정, 수백 개의 행동 공변량이 있는 디지털 광고 증분 효과 측정, 처치 단위 수보다 통제변수 후보가 훨씬 많은 행정 데이터 정책 평가. 같은 틀이 인과 숲과 R-learner를 통해 이질적 효과로 확장되고 현대적 업리프트 모델링이 그렇게 만들어집니다.
Pricing and demand estimation with rich product and customer attributes where theory does not specify which confound; digital advertising incrementality with hundreds of behavioural covariates; policy evaluation on administrative data where candidate controls dwarf the number of treated units. The same framework extends to heterogeneous effects via causal forests and the R-learner, which is how modern uplift modelling is built.
시리즈를 닫으며Closing the series
스물네 편, 중심극한정리에서 이중 머신러닝까지. 관통하는 줄이 하나 있다면 이것입니다. 여기 모든 방법은 가정이 성립하든 아니든 숫자를 내놓고 그 숫자는 뒤에 있는 가정만큼만 좋습니다.
Twenty-four posts, from the Central Limit Theorem to double machine learning. The through-line, if there is one: every method here produces a number regardless of whether its assumptions hold, and the number is only as good as the assumption behind it.
기초 섹션의 잘못 설정된 모형 편이 가장 깨끗한 예입니다. R² 0.76, t값 11 이상, 깨끗한 잔차 진단, 그리고 참값에서 27% 벗어난 추정치. 아무것도 그것을 표시해 주지 않았습니다. 인과추론 섹션은 본질적으로 가정을 더 방어 가능하게 만드는 방법들의 목록입니다. 머신러닝 섹션은 변수 수가 하나하나 따져 볼 수 있는 범위를 넘어설 때에도 그 규율을 유지하는 방법을 다룹니다.
The misspecification post in the Basics section is the cleanest illustration: R² of 0.76, t-statistics above 11, clean residual diagnostics, and an estimate 27% away from the truth. Nothing flagged it. The Causal Inference section is essentially a catalogue of ways to make the assumption more defensible, and the Machine Learning section is about keeping that discipline as the number of variables grows past what you can reason about individually.
도구는 바뀝니다. 이 자료를 처음 가르칠 때 Double LASSO는 없었고 언젠가 다른 것이 이것을 대체할 것입니다. 바뀌지 않는 것은 추정량이 무엇을 요구하는지 적어 두고 그것이 돌려주는 숫자를 믿기 전에 직접 확인하는 습관입니다.
The tools change. Double LASSO was not available when this material was first taught, and something else will supersede it. What does not change is the habit of writing down what the estimator requires and checking it directly, before trusting the number it returns.