The theorem-backed contract#

This page carries what Theorem 1 states, the objects it is stated over, and the conditions it rests on. Targeting and cross-fitting carries what the implementation chooses where the theorem is silent. Every source and locator is in references.

The objects#

For treatment level a, with Q̄_0(a, w) = E_0(Y | A = a, W = w), the target is ψ_0(a) = E_0{Q̄_0(a, W)} and ATE = ψ_0(1) − ψ_0(0). The ordinary efficient influence function is D*(Q, g)(O) = A/g(W)·{Y − Q̄(W)} + Q̄(W) − Ψ(Q).

The default construction uses three univariate reduced regressions however many covariates the fit adjusted for:

Q_r    := Q̄_{0,r}(Q̄, g)(w)      = E_0[ Y − Q̄(W) | A = 1, g(W) = g(w) ]
g_{r,1} := g_{1,0,r}(Q̄)(w)       = E_0[ A | Q̄(W) = Q̄(w) ]
g_{r,2} := g_{2,0,r}(Q̄, g)(w)    = E_0[ (A − g(W))/g(W) | Q̄(W) = Q̄(w) ]

The two corrections, in the orientation this package computes and the appendices derive:

D_A = D*_g = (Q_r/g)·{A − g}
D_Y = D*_Q = 1_a·(g_{r,2}/g_{r,1})·{Y − Q̄}

The bivariate alternative retains Q_r and replaces both reduced mechanisms by one probability:

g_r(a|w) = P_0{A=a | Qbar(a,W)=Qbar(a,w), g(a|W)=g(a|w)}
D_Y      = 1_a·{g_r(a|W)-g(a|W)}/[g(a|W)g_r(a|W)]·{Y-Qbar(a,W)}

This is exactly the pinned R source’s two-column estimategrn branch, fluctuateQ2 clever covariate, and eval_Dstar_Q correction. Those branches loop over every requested level of a discrete treatment, so cleverly uses the same one-versus-rest probability and correction for each arm. In the stored state gr1 is that probability and gr2 is NaN, because the latter regression does not exist on this path; using zero would make an accidental univariate formula look valid.

and the limiting influence function

D^{*,#}(Q, g) = D*(Q, g) − I(g = g_0)·D_A − I(Q̄ = Q̄_0)·D_Y

The indicators contain the doubly-robust claim. At the true primary nuisance functions, both corrections vanish and the ordinary efficient influence function is recovered.

The two extra score equations, as the software article states them:

(9)   P_n[ Q_r(a,W)/g*(a|W) · {1_a − g*(a|W)} ]                    = 0
(10)  P_n[ 1_a · g_{r,2}(a|W)/g_{r,1}(a|W) · {Y − Q̄*(a,W)} ]        = 0

Theorem 1#

Suppose either Q̄ = Q̄_0 or g = g_0, and let the targeted collection (Q̄*_n, Q̄*_{n,r}, g*_n, g*_{1,n,r}, g*_{2,n,r}) satisfy the three empirical score conditions

B_n     = P_n D*(Q*_n, g*_n)                            = o_p(n^(−1/2))
B_{A,n} = P_n D_A(Q̄*_{n,r}, g*_n)                       = o_p(n^(−1/2))
B_{Y,n} = P_n D_Y(Q̄*_n, g*_{1,n,r}, g*_{2,n,r})         = o_p(n^(−1/2))

and suppose the appendix remainder terms satisfy R_{Q,n} = o_p(n^(−1/2)) and R_{g,n} = o_p(n^(−1/2)). Then the targeted plug-in is asymptotically linear with influence function D^{*,#}, and √n(ψ̂ − ψ_0) ⇝ N(0, σ²) with

σ̂²_n = P_n [ D*(Q*_n, g*_n) − D_A − D_Y ]²

Four things to read off it:

  • the remainder conditions do not follow from the union condition and the rates. The conditioning terms shows why. With one nuisance wrong, the interval is established only in the cases that section lists;

  • the score conditions are o_p(n^(−1/2)), not exact zeros. This implementation’s exact-zero ambition is stricter than the theorem, and its numerical stopping rule is not obviously either;

  • the conditions are on the targeted collection, including the starred reduced nuisances, which is why retarget on a DRTMLE result costs a fit rather than arithmetic on cached arrays. That cost follows the source, and is not a design slip;

  • the variance is P_n[·]² of the rowwise corrected curve, so nothing that summarises the curve before squaring is computing this. The ATE curve is the rowwise difference of the two arm curves, which is what makes an ATE-only diagnostic insufficient: arm-specific errors cancel in a difference.

tests/unit/test_theorem_drtmle.py::TestTheReportedVarianceIsTheorem1s pins the last property. The interval built from the package’s own corrections is the one Theorem 1’s terms give. The uncentred P_n{D}² differs from the reported variance by exactly (P_n D)², and the contrast reads the covariance rather than the sum of the arms.

A known treatment mechanism#

Data can declare its treatment mechanism with treatment_probabilities= (the point-treatment contract gives the forms). A complete-data fit is then Theorem 1 at the degenerate estimator g_n ≡ g_0. The branch g = g_0 of the theorem’s hypothesis holds by declaration, and R_{g,n} is trivial at g_0. This is a case where the interval with a wrong outcome regression is established (the conditioning terms). The ordinary TMLE interval is valid here too.

guard

what the fit does with the declared g_0

()

the ordinary TMLE at g_0, which is exact for any Q̄

("g",)

equation (10) fluctuates Q̄ only, so the mechanism stays g_0

("Q",) and ("Q", "g")

equation (9) fluctuates g* along Q_r/g (step 6 of the algorithm in Benkeser et al. 2017, Section 3.2), so g* moves off g_0 on purpose

Under the "Q" guard the reported curve D* − D_A − D_Y is the curve of the estimator that fluctuates a known mechanism. It is not the curve of the known-mechanism TMLE. R drtmle 1.1.2 does the same with a supplied gn: its gnStar starts at gn, and fluctuateG moves it. The fluctuated g* is no longer the declaration, so it keeps the shipped truncation. The declaration itself answers to the bound rule of the point-treatment contract before any learner.

At an exact law the "Q" guards are blind. There P_n D_A = 0 at g_0 before any fluctuation, so equation (9) solves at ε_g = 0 whether the fluctuation exists or not. tests/unit/test_known_treatment_mechanism.py therefore checks the fluctuation on a finite sample: the initial P_n D_A exceeds 1e-3, the final score is solved, and max |g* − g_0| exceeds 1e-4.

Every reduction and both reduced_crossfit settings admit a declared mechanism. The nested construction reuses g_0 in every inner fold, because a declared mechanism does not depend on the rows a model saw. An evaluation= companion must declare the same columns. The registered known-mechanism DR-TMLE study pairs each guard with R drtmle (gn=) at a wrong outcome regression.

The statements above are for complete data. With delta=, the declaration supplies the treatment mechanism g_A only, and the fit still estimates the observation mechanism g_Delta. The table gives what follows for the randomized missing-outcome route.

question

answer

the remainder with a wrong outcome regression

linear in the error of g_A g_Delta, not a product of two errors. The term sits in the step at equation (21) of the proof in Díaz and van der Laan (2017), Appendix A.1. A known g_A does not remove it, because g_Delta is estimated

the measured effect

a project probe simulated a known g_A, a wrong outcome regression and a slowly converging g_Delta. Coverage of ey[1] fell to 0.850 at n = 16,000, and the bias grew with n (reviews/rm40/lra_summary.log, not a registered study). The registered one-inconsistent-nuisance study repeats the setting on law M at n = 4,000. Its arm-mean bias was −0.53 and −0.54 SD, with coverage 0.920 and 0.926

when the interval is established

when the outcome regression and g_Delta are both consistent

what a declared g_A alone gives

no established interval with a wrong outcome regression. This is a gap in the theory, not in the evidence

n_bootstrap=

admitted, as on the route with an estimated g_A. A full-refit bootstrap resamples the same estimator, so its range rests on the same remainder as the analytic interval and carries the same limit

Randomized trials with missing outcomes#

For observed data O=(W,A,Delta,Delta Y), write g_A(a|W)=P(A=a|W), g_Delta(a,W)=P(Delta=1|A=a,W), and g=g_A g_Delta. Díaz & van der Laan’s efficient influence function is

D* = 1(A=a, Delta=1)/g · {Y − Qbar(a,W)} + Qbar(a,W) − psi(a).

The implementation keeps the five one-dimensional regressions and the three correction blocks in the paper separate:

gamma_A = P(A=a | Qbar_a)
gamma_Delta = P(Delta=1 | A=a,Qbar_a)
r_A = E[{1(A=a)-g_A}/g_A | Qbar_a]
r_Delta = E[{Delta-g_Delta}/(g_A g_Delta) | A=a,Qbar_a]
e = E[Y-Qbar_a | A=a,Delta=1,g_A g_Delta]

D_A = e/g_A · {1(A=a)-g_A}
D_Delta = 1(A=a)e/(g_A g_Delta) · {Delta-g_Delta}
D_Y = 1(A=a,Delta=1) · {r_A/(gamma_A gamma_Delta)+r_Delta/gamma_Delta}
      · {Y-Qbar_a}

The targeting cycle jointly updates the ordinary outcome and D_Y covariates, updates g_Delta within each arm, updates g_A, refits all five reductions, and repeats until all four score blocks settle. The g_A update takes one of two routes, and both solve the equation P_n[e_a/g_a · {1(A=a) − g_a}] = 0 for every arm.

arms

g_A update

covariate

two

one two-parameter logistic tilt of g_1, with g_0 = 1 − g_1

(−e_0/g_0, +e_1/g_1)

three or more

one logistic tilt of each column g_a, with the response 1(A=a), on all rows

+e_a/g_a

At two arms the arm-0 column carries a minus sign, because its score −(e_0/g_0)(A − g_1) equals (e_0/g_0){1(A=0) − g_0}. Above two arms the tilted columns are not renormalized. They are nuisance denominators and not an intervention. correction_check reports D_A, D_Delta and D_Y separately; checking only D_A + D_Delta would be blind to equal and opposite score errors. Missing-outcome fits therefore require guard=("Q", "g").

Treatment probabilities and observation probabilities retain their own bounds: g_bounds applies to g_A and gamma_A, while nuisance_bound applies to g_Delta and gamma_Delta. Their product is derived for the ordinary outcome clever covariate and the positivity report, never stored as a third nuisance. The treatment truncation curve moves only the treatment bound; mechanism=True moves only the observation bound.

The positivity report’s P(A=a,Delta=1|W) row is derived, so it has no bound of its own. Reading it as though it did is a mistake worth naming. Each factor is truncated and the two are then multiplied, so the product is never compared against g_bounds[0] × nuisance_bound. That row’s clipped therefore counts the cells where either factor’s truncation moved the product. Its ess_ratio weights by clip(g)·clip(π), so the denominator the equation forms. Counting against the product of the floors instead reports a strict subset, since a small factor beside a large one leaves the product above it: measured at 1.1% against a true 20.1% on the pinched fixture in tests/unit/test_drtmle_missing.py.

The shipped scope follows the paper rather than the broader canonical package: randomized treatment at any number of arms, MAR and positivity, no cross-fitting, and no weights, repeats, fold targeting, or evaluation companion. randomized=True estimates g_A. Data that declares its mechanism (a known treatment mechanism) supplies g_A and fits no treatment learner. An observational missing outcome and a missing treatment take the construction of the composite indicator instead.

With a wrong outcome regression the theorem does not establish the interval in general. The proof of Theorem 1 is in Appendix A.1 of Díaz and van der Laan (2017). It conditions a residual mean on the pair (g_0, ĝ). It then replaces that mean by one given g_0 alone, and calls the difference, the term at equation (21), O_P(‖ĝ − g_0‖²). The difference is linear in ĝ − g_0 when the error of ĝ breaks the level sets of g_0. Lemma 1 and Theorem 2 inherit the step. Here g = g_A g_Delta, so the term has the same structure as R_{3,n} of the conditioning terms.

observation mechanism, with the outcome regression wrong

the interval

the product mechanism g_A g_Delta known

established. The package always estimates g_Delta, so no fit is in this row

a correctly specified parametric model

the projection argument of the conditioning terms suggests a conservative interval. The page derives it for a complete outcome only. A re-check of the probe’s GLM cell (n = 4,000, R = 1,000) found no bias: every 99% bias interval contains zero, and the SE ratios are 0.96 to 1.01 (reviews/rm40/lra_recheck.log, not a registered study)

a data-adaptive learner

not established. A project probe found an arm-mean bias that grows with n. The law-M control of the registered one-inconsistent-nuisance study shows the bias at n = 4,000

The probe declared g_A, fitted a wrong outcome regression, and gave g_Delta a constructed slow error (reviews/rm40/lra_summary.log). The ey[1] bias was −0.24, −0.60 and −0.98 SD at n = 1,000, 4,000 and 16,000. Its SE ratio stayed between 0.88 and 1.10. A known g_A alone is not enough.

The ate bias cancelled on that law, because the errors of both arms moved the same way. The mirror branch, where r̂_{A,0} and r̂_{M,0} condition on (m_1, m̂), has the same structure. No probe measured it.

More than two arms#

Díaz and van der Laan (2017) state their result for one arm indicator. Above two arms, the fit applies it to each indicator 1(A=a) and stacks the arm estimators. The contract below gives the argument in five parts. Page numbers are those of the arXiv v1 author manuscript that the references cite.

part

content

base result

Theorem 2 (p. 20) under Condition 2 (Donsker, p. 13) and Condition 3 (p. 15). It gives n^(1/2)(psi_dtmle − psi_0) → N(0, Var D_dr) with D_dr of Theorem 1 (p. 16), for one indicator A and the target E(Y_1). Section 2.1 (p. 6) applies it to “four such indicators” in its application. With a wrong outcome regression the result holds only in the cases above, because the proof’s step at equation (21) is linear in ĝ − g_0

steps

indicator reduction: arm a uses (W, 1(A=a), Delta, Delta Y) and its own `g_A(a

objection search

p. 25 rejects a composite T = AM reduction. The armwise construction keeps g_A and g_Delta apart, so the objection does not apply. p. 26 discusses cross-fitting, not arms. No source records the indicator reduction or the stack as open

conditions

Assumptions 1 to 4 (pp. 6-7) at every arm, with positivity `g_A(a

evidence

the exact-law checks, nonzero witnesses, mutation controls and independent reference of tests/unit/test_drtmle_missing_multi_arm.py, and the registered multi-arm missing-outcome study

No fluctuation parameter is shared across arms above two arms. This condition is what lets each arm’s expansion hold inside the joint loop. Theorem 2’s proof uses only that arm’s solved equations and Conditions 2 and 3. Four places carry the condition.

block

where it is per arm

outcome tilt

missing_outcome_outcome_submodel builds a zero block for every other arm

observation tilt

_solve_missing_observation_mechanism tilts g_Delta within each arm

reductions

fit_missing_outcome_reduced fits each arm’s five regressions on that arm’s columns

treatment tilt

solve_armwise_bounded_mechanism tilts each column g_a alone

The loop stops on the largest score over all arms, and so does the final check. That rule is stricter than Theorem 2’s per-arm requirement. At two arms the one shared tilt of g_1 is a different path to the same two solved equations. The proof reads only the solved equations, so the result holds there too.

Observational missing data: the composite indicator#

An observational fit with delta= and a fit with a missing treatment use one construction. The fit declares a missing treatment with treatment_delta=<column>, the 0/1 column that is 1 where the treatment is recorded. The package never infers a missing treatment from a missing value, for the reason it never infers a missing outcome: an accidental gap must not start a missing-data analysis. The roadmap words for this item read “a missing treatment coded as a missing value”, and the declaration is a deliberate deviation from them.

For arm a, write Delta_A for the treatment indicator and define the composite indicator and its mechanism:

C_a = Delta_A · Delta · 1(A=a)
g_c,a(W) = P(C_a=1 | W) = pi_A(W) · g(a | Delta_A=1, W) · pi(a, W)
pi_A(W) = P(Delta_A=1 | W),    pi(a, W) = P(Delta=1 | A=a, Delta_A=1, W)

The product is the law of total probability, so it holds for every law. No factor needs a causal reading. The fit estimates each factor on the rows it conditions on, and the outcome regression on the rows where C_a can be 1.

The route. cleverly.estimators.composite.missing_data_route chooses the construction, and the fit records it under result.extra["missing_data"].

delta=

missing treatment

randomized=True, or a declared mechanism on DRTMLE

guard

route

no

no

any

any

complete

yes

no

yes

non-empty

randomized_missing_outcome (Díaz and van der Laan above)

yes

no

no

non-empty

composite

yes

no

any

(), or TMLE

missing_outcome (the shipped missing-outcome TMLE)

any

yes

no

any, or TMLE

composite

any

yes

yes

any

refused: randomized=True selects a construction that observes the treatment on every row, and a declared mechanism is not the mechanism of the recorded rows

A per-arm outcome-adaptive CTMLE fit takes the missing_outcome route with delta= alone, and the composite route with a missing treatment, in sample only. Its factors regress on Qbar_n(a, W) and not on W, and the fit reports a point estimate only. The collaborative TMLE reference states that contract. The other C-TMLE strategies refuse a missing treatment.

The contract has five parts.

part

content

base result

Benkeser, Carone, van der Laan and Gilbert (2017), Section 3.2, Theorem 1: on O = (W, A, Y) with a binary A, the estimator that solves the targeting equation and the equations of the reduced regressions is asymptotically linear with curve D* − D*_Q − D*_g under the theorem’s score and remainder conditions. Both nuisances consistent meet them. With one nuisance wrong, the conditioning terms limit the claim to the cases listed there, applied to (W, C_a, C_a Y) with the composite mechanism g_c,a

steps

indicator reduction: Theorem 1 applies as stated to O'_a = (W, C_a, C_a Y), with the binary treatment C_a, the mechanism g_c,a and the regression `E(Y

objection search

Benkeser et al. (2017) mention no missing data and no caveat about coarsening. Díaz and van der Laan (2017, p. 25) reject a composite T = AM for a randomized trial, because it discards known design information. On an observational law nothing about the treatment mechanism is known, so the composite discards nothing. R drtmle 1.1.2 implements this construction (R/drtmle.R lines 207-209, R/fluctuate.R lines 28, 98 and 169-172, R/estimate.R lines 116-200)

conditions

the four conditions below; Theorem 1’s conditions for each arm on O'_a, which include the Donsker condition, hence cross_fit=False; the solved equations of every arm at o_P(n^(−1/2)). The loop stops on the largest score over the arms, which is stricter than the per-arm requirement

evidence

the exact-law checks, nonzero witnesses, mutation controls and per-arm reference of tests/unit/test_composite_missing_data.py, and the registered composite study

The conditions are these.

condition

statement

consistency and no unmeasured confounding

Y = Y(a) when A = a, and Y(a) is independent of A given W

treatment missing at random

Y(a) is independent of Delta_A given (A, W)

outcome missing at random

Y is independent of Delta given (A, Delta_A=1, W)

composite positivity

g_c,a(W) > 0 for every arm, and W complete on every row

What the data do not identify. The conditions let Delta_A depend on A. Then P(A = a | W) is not identified, and only P(A = a | Delta_A = 1, W) is. A target or a clever covariate that reads the treatment law of every row is therefore not identified with a missing treatment. That covers att, atc, ey_obs, par, paf, incremental= and policies=. The shared preflight refuses each one by name, and each refusal repeats this statement. A regime mean and an arm-indexed msm= coefficient read only the outcome regression and the law of W, so the composite identifies them.

No observed-data check can detect a violation of the treatment condition.

The carrier. g_c,0 + g_c,1 < 1 whenever a row can be unrecorded, so the composite is not a distribution over the arms. It always travels as an (n, K) mechanism off the simplex. Every site that tilts or reads a two-arm mechanism uses one rule: the mechanism is one column exactly when the two-arm complement form applies. The composite therefore tilts each arm’s column alone at every arm count, two included. No fluctuation parameter is shared across arms.

The bounds. Each factor is bounded as the shipped missing-outcome TMLE bounds it: the treatment factor by g_bounds, and each observation factor below by nuisance_bound. The composite is then tilted and clipped inside [g_lo · nb^k, g_hi], where k counts the observation factors. That floor is the smallest product of the bounded factors, so the initial clip moves no value. At g_bounds=(0.01, 0.99) and nuisance_bound=0.01 with both indicators, the floor is 0.01 · 0.01² = 1e−6, against 1e−4 on a missing outcome alone. The default g_bounds="auto" sets g_lo = 5 / (sqrt(n) ln n) instead. The positivity report adds the composite row with its minimum and the share of unit-arm cells below g_lo.

The rejected alternative floors the composite at g_lo after the tilt, as R drtmle’s tolg floors its product. That floor clips legitimate products of three probabilities. It also breaks an exact reduction: without a missing treatment the composite’s initial covariate is the shipped missing-outcome covariate 1(A=a) Delta/(g pi) bit for bit, and that covariate is not floored at g_lo.

The sign of the mechanism correction#

The implementation’s sign is the derived one, on the working paper’s own appendices. Only a variance check could have caught this. All three empirical means are driven to zero, so a flipped sign moves the variance and leaves the point estimate alone.

The discrepancy. The §3.1 display defines D_A := −(Q_r/g)(A − g), with a leading minus. Theorem 1 then reports D^{*,#} = D* − D_A − D_Y. Read off those two displays, the theorem’s mechanism contribution is +u where the code’s is −u.

What settles it. The same paper prints the object twice with two signs. §3.2 redefines D_Y for the univariate construction, which is the default here, with no leading minus. That is twelve lines after printing the bivariate one with one. Two displays of one object with opposite signs is already a reason not to settle the question from a display.

Appendices A and B decide it. Each derives one term, and each derivation fixes the orientation. Each reads P_0[term] = −(P_n − P_0)·D + B_n + (second order) with B_n := P_n·D. For any u whatever, P_0[u] = P_n[u] − (P_n − P_0)[u] is an identity. The decomposition is therefore satisfiable only with D equal to the positive term. Appendix A’s opening step names the quantity being decomposed, and it is checkable rather than interpretable:

−P_0{ (Q_r/g_0)·(g_n − g_0) } = P_0{ (Q_r/g_0)·(A − g_n) }      since E_0[A | W] = g_0

The right-hand side is positive. tests/unit/test_theorem_drtmle.py checks that identity on the exact law. It also checks that the correction’s mean is materially nonzero there, because a zero mean would make both readings agree and the question unanswerable. The test then checks the consequence. The asymptotic-linearity representation closes to 1e-12 with the corrections subtracted, and fails by exactly twice the correction when they are added. Three mutations are watched to fail it, one of them the flipped sign in the library itself.

The leading minus in the §3.1 display is therefore not a rival convention to match. It contradicts the derivation in the same document, Theorem 1’s own variance formula, and the exact-law arithmetic here. The published 2017 article confirms the corrected constructions. It does not replace that algebraic sign witness. The code follows the identity rather than a display in either edition.

Two further sign slips sit in the same document. Equation (2) prints +(P_n − P_0)D − B_n where its appendices derive −(P_n − P_0)D + B_n, which is the same slip under D → −D. Equation (2) also crosses its second-order labels: appendix A’s block is the D_A one and is collected into R_{Q,n}, while (2) pairs D_A with R_{g,n}. Neither affects the implementation, which reads no label. Both are worth knowing before you quote (2).

Appendix C: a correction that is not needed costs nothing#

The paper’s own account of why solving an equation you did not need is asymptotically free. Both answers rest on a vanishing:

D_A = 0  for every g,   because Q_r    = 0 when Q̄ = Q̄_0
D_Y = 0  for every Q̄,   because g_{r,2} = 0 when g  = g_0

Each B then decomposes into an empirical-process term plus a second-order one, both o_p(n^(−1/2)) under the appendices’ rate conditions.

This is also the source of the blindness that shapes every test on this estimator. Q_r and g_{r,2} are zero row by row at correct nuisances. Any check taken at the truth is therefore blind to a flipped sign, to an update order, and to a reduction vintage alike. That is why tests/unit/test_theorem_drtmle.py and tests/unit/test_influence_gateaux_drtmle.py are taken at values where the corrections do not vanish, and why their fixtures are misspecified on purpose.

The remainder terms, and the rate conditions#

The mechanism-misspecification branch, appendix B:

R̃_{5,n} = P_0[ { (A/g_{1,0n,r})·g_{2,0n,r} − (A/g_{1,0,r})·g_{2,0,r} } · (Q̄_0 − Q̄_n) ]
R̃_{6,n} = P_0[ { (A/g_{1,0,r})·g_{2,0,r}   − (A/g_{1,n,r})·g_{2,n,r} } · (Q̄_0 − Q̄_n) ]
M̃_{2,n} = (P_n − P_0)[ D_Y(Q̄_n, g_{1,n,r}, g_{2,n,r}) − D_Y(Q̄_0, g_{1,0,r}, g_{2,0,r}) ]
R_{g,n} = R̃_{5,n} + R̃_{6,n} + M̃_{2,n}

The published displays carry the factor (Q̄_0 − Q̄_n). The leading A makes (Y − Q̄_n) give the same P_0 value, because E_0[A(Y − Q̄_n) | W] = E_0[A(Q̄_0 − Q̄_n) | W].

The outcome-misspecification branch, appendix A, R_{Q,n} = R_{3,n} + R_{4,n} + M_{1,n}:

R_{3,n} = P_0[ { (Q̄_{0n,r} − Q̄_{0,r}) / g_0 } · (g_0 − g_n) ]
R_{4,n} = P_0[ { Q̄_{0,r}/g_0 − Q̄_{n,r}/g_n }  · (g_0 − g_n) ]
M_{1,n} = (P_n − P_0)[ D_A(Q̄_{n,r}, g_n) − D_A(Q̄_{0,r}, g_0) ]

with Q̄_{0n,r}(w) := E_0{Y − Q̄(W) | A = 1, g_n(W) = g_n(w), g_0(W) = g_0(w)} evaluated at the estimated propensity as well as the true one, which is what makes R_{3,n} an approximation error rather than a fitted one. The published display omits A = 1 under the paper’s “abuse of notation”. The first equality of the same display needs it, because it rewrites P_0{(A/g_0²)(Y − Q̄)(g_n − g_0)} as P_0{(Q̄_{0n,r}/g_0)(g_n − g_0)}. Appendix A also carries R*_n = R_{1,n} + R_{2,n}, the part that is second order whichever nuisance is right.

The paper states these rates as sufficient conditions. It states that it generally suffices that, for R_{g,n}:

‖Q̄_n − Q̄_0‖_2 = o_p(n^(−1/4))
‖g_{2,0n,r} − g_{2,0,r}‖_2 = o_p(n^(−1/4))
‖g_{2,n,r}  − g_{2,0,r}‖_2 = o_p(n^(−1/4))

and for R_{Q,n}, in the same “if, for example” form, o_p(n^(−1/4)) on the reduced regression’s approximation error ‖Q̄_{0n,r} − Q̄_{n,r}‖_2, on its fitted error ‖Q̄_{n,r} − Q̄_{0,r}‖_2, and on the primary propensity’s error ‖g_n − g_0‖_2. Both appendices add an empirical-process pair in one shape: a P_0-Donsker class containing the estimated curve, plus L_2(P_0) convergence of the estimated curve to its limit. The next subsection shows that two of these rates need not hold when one nuisance is wrong.

These are conditions on estimated functions that no fit can check for itself.

The conditioning terms are linear in one error#

R_{3,n} and R̃_{5,n} are not products of two errors. Each one is linear in the error of the consistent nuisance. The rates above make neither term negligible when the other nuisance is wrong. The tables below state when each term vanishes.

The notation is for arm 1. Arm 0 replaces g by 1 − g throughout. Q̄ and ḡ are the limits of Q̄_n and g_n. Write Q̄_{0,r} = E_0[Y − Q̄ | A = 1, g_0(W)] and F = Q̄_0 − Q̄ − Q̄_{0,r}.

The outcome branch. On a level set of (g_n, g_0) the probability P(A = 1 | W) = g_0 is constant. Conditioning on A = 1 therefore leaves the law of W unchanged there, and Q̄_{0n,r} = E_0[Q̄_0 − Q̄_n | g_n, g_0]. The factor (g_0 − g_n)/g_0 is a function of (g_n, g_0). The tower rule gives, with no approximation,

R_{3,n} = P_0[ (Q̄_0 − Q̄_n − Q̄_{0,r})/g_0 · (g_0 − g_n) ]

The first factor tends to F. F is zero only when Q̄_0 − Q̄ is a function of g_0. So R_{3,n} is linear in g_n − g_0.

The paper’s own premise for R_{4,n} is that the fitted reduction converges to Q̄_{0,r}. Under that premise R_{3,n} is the first-order leftover of the estimator. The paper puts o_P(n^(−1/4)) on ‖Q̄_{0n,r} − Q̄_{n,r}‖_2. For an error of g_n that breaks the level sets of g_0, that norm stays of order one. The implication is correct, and its premise fails in the generic one-wrong case.

Only the bias of the error moves the centre of the estimate. The stochastic part of g_n − g_0 has mean zero. It changes the variance, as the projection shows. A first-order bias needs a bias of g_n of order r_n ≫ n^(−1/2) along F/g_0.

Finite support. On a law with discrete covariates, an estimate can break a tie of g_0. The exact reduction E[· | g_n] can then recover the whole residual, so that R_{4,n} = −R_{3,n} and the leftover vanishes. The tables below are for laws where the conditional mean given g is continuous in g.

The mechanism branch. Appendix B states the exact step P_0{(Q̄_n − Q̄_0)(g − g_0)/g} = −P_0{g_{2,0n,r}(Q̄_n − Q̄_0)}. There g_{1,0n,r} and g_{2,0n,r} condition on (Q̄_n(W), Q̄_0(W)). After equation (10) the leftover reduces to P_0[h·(Q̄_0 − Q̄_n)], with

r = (g_0 − ḡ)/ḡ,    h = r − g_0·E[r | Q̄_0]/E[g_0 | Q̄_0],    E[h | Q̄_0] = 0

It is linear in Q̄_n − Q̄_0.

When the term adds no first-order bias. The table is for the univariate reduction. The first three rows make the term o_P(n^(−1/2)). Negligible bias leaves a stochastic part of order n^(−1/2). Its effect on the interval is derived only for a parametric index, where it makes the interval conservative.

condition

outcome branch (Q̄ wrong)

mechanism branch (g wrong)

checkable from a fit

both nuisances consistent at the product rates

the first factor shrinks too

the same

no. This is the ordinary TMLE rate condition

H2: the consistent estimate keeps the level sets of its truth

g_n = g_0, or g_n = φ_n(g_0) with φ_n tending to the identity

Q̄_n = φ_n(Q̄_0)

yes for a declared known mechanism. Otherwise no

H1

Q̄_0 − Q̄ is a function of g_0

1/ḡ − 1/g_0 is a function of Q̄_0, which is h ≡ 0

no

negligible bias

the bias of g_n along F/g_0 is o(n^(−1/2))

the bias of Q̄_n along h is o(n^(−1/2))

no

For arm 0, the outcome-branch H1 is: Q̄_0(0, ·) − Q̄(0, ·) is a function of g_0. The mechanism-branch H1 is: 1/(1 − ḡ) − 1/(1 − g_0) is a function of Q̄_0(0, ·). A limit ḡ that is constant on the level sets of Q̄_0 need not meet it.

Law L has W1, W2 ~ N(0, 1), g_0 = expit(0.6 W1 + 0.3 W2) and Q̄_0 = expit(−0.2 + 0.5 A − W1 + 2 W2). tests/unit/test_drtmle_h1_symmetry.py pins a constant ḡ on law L for which L_2(h) is 0.305.

g_n = φ_n(g_0), with φ_n tending to the identity, is a one-wrong case where the DR-TMLE interval holds and the plain TMLE interval does not. The plain TMLE leftover there is P_0[(g_0 − g_n)/g_n · E(Q̄_0 − Q̄ | g_0)], which is first order. Equation (9) removes it.

The case table. The rows are for the univariate reduction and a binary treatment. Above two arms each row applies arm by arm.

case

conditioning term

reported interval

evidence

both nuisances consistent at the product rates, plus the reduced-regression and solve conditions

second order

valid (Theorem 1)

the registered both-correct cells of the canonical, stratified and multi-arm studies

Q̄ wrong, g declared known

second order (its first-order part is zero). Equation (9) moves g* along Q_r/g_0, a function of g_0

valid. The ordinary TMLE interval is valid too

Theorem 1 at g_n = g_0, the registered known-mechanism DR-TMLE study with a wrong outcome regression, and the declared-mechanism cells of the registered one-inconsistent-nuisance study

Q̄ wrong, g_n = φ_n(g_0) with φ_n tending to the identity, or H1

second order (its first-order part is zero)

valid under the remaining rates

the derivation. The Section 5.1 law of the paper is H1 (tests/unit/test_drtmle_h1_symmetry.py)

Q̄ wrong, g a correctly specified fixed-dimension parametric model fitted by maximum likelihood, in sample or cross-fitted

O_P(n^(−1/2)), linear in the score

conservative: asymptotically linear, with a reported variance too large by c'I^(−1)c

the derivation below, and the registered one-inconsistent-nuisance study: an ATE SE ratio of 1.161 in sample and 1.191 cross-fitted at n = 4,000, with coverage 0.975 and 0.982

Q̄ wrong, g with a bias of order r_n ≫ n^(−1/2) along F/g_0

of order r_n

not established

the identity, and the registered one-inconsistent-nuisance study: a constructed level-set-breaking error of order n^(−1/3) gave an ATE bias of −0.65, −0.86 and −1.16 SD, with coverage 0.935, 0.917 and 0.843, at n = 1,000, 4,000 and 16,000. A cross-fitted gradient-boosting mechanism gave +1.53, +2.01 and +1.51 SD, with coverage 0.75, 0.63 and 0.81. There Q_r is fitted on g_n, so R_{4,n} is first order too (a data-adaptive mechanism)

Q̄ wrong, g fitted in sample by a learner whose own-row term is not negligible

an own-row term, measured larger than the conditioning term and of the opposite sign

not established

the probe in a data-adaptive mechanism: an in-sample gradient-boosting mechanism gave −1.22, −2.28 and −2.50 SD, with coverage 0.75, 0.41 and 0.41

g wrong, Q̄ a correctly specified parametric model

O_P(n^(−1/2))

not established. An extra first-order term of no fixed sign remains, because the target depends on the parameters of Q̄

the derivation only

g wrong, Q̄ with a bias along h of order larger than n^(−1/2)

linear

not established

the identity, and the registered study: a constructed error gave an ATE bias of −0.88, −1.07 and −1.35 SD, with coverage 0.825, 0.789 and 0.687, at the same sizes

PointTreatment(treatment_adjustment=...) is a source of the mechanism-wrong rows. The treatment mechanism then reads a subset of the adjustment set, and it is inconsistent when the restriction fails. Treatment-mechanism covariates gives the restriction text and the pinned summary line.

No fit can tell which row it is in, except a declared known mechanism. The registered study publishes a verdict for each measured row, and its page gives the rules. The earlier project probe, reviews/rm40/drdr_sim.py with its log reviews/rm40/drdr_summary.log, agrees with it. The registered multi-arm study has a law that no test pins as H1, and a correctly specified multinomial mechanism. Its SE ratios of 1.00 to 1.04 do not contradict the conservative row. Its verdicts cannot detect a conservative interval, because its coverage rule is a floor.

One registered study detects the term. The one-inconsistent-nuisance study uses law L, which is not H1 in either branch. The verdicts of the other studies cannot detect it. The canonical and stratified laws are H1 in both branches by symmetry, as tests/unit/test_drtmle_h1_symmetry.py pins. The missing-data studies give the consistent nuisance as an exact law table, which is H2.

The routes. DR-TMLE is the only shipped family that publishes an interval exposed to this term. Its status stays influence_curve on every route, because a fit cannot tell which case it is in, and the interval is valid when both nuisances are consistent at the product rates.

route

index of the conditioning term

one-wrong interval established when

evidence

complete outcome: binary, more arms, strata, fixed weights, clusters, both reductions

g_n with the outcome wrong, Q̄_n with the mechanism wrong

the case table above

the registered one-inconsistent-nuisance study, and the probe log reviews/rm40/drdr_summary.log

randomized missing outcome

the product ĝ_A ĝ_Delta

the product mechanism is known. A known g_A alone is not enough

reviews/rm40/lra_summary.log, and the law-M control of the registered study: with g_A declared and a slow observation mechanism, an arm-mean bias of −0.53 and −0.54 SD

composite indicator

the composite mechanism g_c,a

the case table above, applied arm by arm to (W, C_a, C_a Y)

the complete-outcome probe applies, because this route is the same theorem on a recoded treatment

results computed from a fit on these routes: variable_importance, E-values, truncation curves, the full-refit bootstrap

inherited from the fit

as for the fit

none

A data-adaptive mechanism#

RM40’s pre-declaration probe found a large DR-TMLE bias with a gradient-boosting mechanism and a wrong outcome regression on law L. The probe reviews/rm41/probe.py finds the cause. Its log is reviews/rm41/probe.log. It is a probe and not a registered study.

setting

value

law

law L

outcome regression

a logistic GLM on (A, W1), which is wrong

mechanism

HistGradientBoostingClassifier with 100 iterations, 15 leaves, 20 rows per leaf and no early stopping

reduced learners

cubic polynomials in the scalar design

fit

g_bounds=(0.01, 0.99), guard=("Q", "g"), reduction="univariate"

size

n = 1,000, 4,000 and 16,000, with 200 draws each

The results apply to this tuning on law L. The probe does not measure other learners or laws. Each number below is an ATE bias divided by the Monte Carlo SD of its cell, unless a row names another SD. The coverage readings have a Monte Carlo SE of at most 0.035. The independent solver keeps only fits whose scores are below 1e-8. At one mechanism fitted on a separate draw, it keeps 98, 187 and 198 of 200 fits at n = 1,000, 4,000 and 16,000.

The bias is a property of the method, not of the code. An independent solver of equations (8) to (10) shares no code with cleverly. The checks below compare it with DRTMLE.

check

result at n = 1,000, 4,000 and 16,000

DRTMLE against the independent solver at one mechanism fitted on a separate draw, paired by draw

a mean difference of −0.06, −0.06 and −0.07 SD

the two update_order values at that mechanism

a mean difference of −0.01, −0.02 and −0.06 SD

the population limit of the solver at that mechanism, against the bias of the solver on the same draws, both divided by the SD of the solver

+1.56, +1.70 and +1.13 SD, against +1.51, +1.66 and +1.03 SD

the independent solver without corrections, against TMLE

equal to 1.7e-12 over 1,800 estimates

The bias has two parts. The first part is in the population limit. The second part comes from the rows that the mechanism was fitted on.

fit

bias at n = 1,000, 4,000 and 16,000

coverage

DRTMLE, cross_fit=True (the default)

+1.53, +2.01, +1.51

0.75, 0.63, 0.81

DRTMLE, cross_fit=False

−1.22, −2.28, −2.50

0.75, 0.41, 0.41

TMLE, the same learners, cross_fit=True

+0.42, +0.32, −0.05

1.000, 0.995, 0.980

TMLE, the same learners, cross_fit=False

−0.18, +0.24, +0.34

0.93, 0.96, 0.98

Part 1: the reduction conditions on the fitted index. Write D = Q̄_0 − Q̄. Equation (9) removes the part of the remainder that is a function of g_n, through Q_r° = E_0[D | A = 1, g_n(W)]. The exact leftover is

P_0[(g_0 − g_n)/g_n · (D − Q_r°)] = E_0[ Cov(g_0, D | g_n) / E_0(g_0 | g_n) ]

This term is linear in the spread of g_0 inside the level sets of g_n. It is zero under H2. The probe splits it into the page’s R_{3,n} and R_{4,n}. It uses a mechanism fitted on a separate draw, so that no row enters its own mechanism.

cell

term

bias at n = 1,000, 4,000 and 16,000

Q_r fitted on g_0 instead of g_n

R_{3,n}: the case-table row for a bias of order r_n along F/g_0

+0.66, +0.50, +0.26

Q_r on g_n minus Q_r on g_0, paired by draw, divided by the SD of the in-sample DRTMLE fit

R_{4,n}: Q_r converges to a regression on g_n, not on g_0

+0.50, +0.95, +0.91

Q_r replaced by its population version on g_n

the fitted error of Q_r

none at n = 4,000 and 16,000: +1.82, +1.78, +1.05 against +1.51, +1.66, +1.03

This part is in the population limit at the fitted mechanism. Cross-fitting, nested reductions and the update order do not remove it.

Part 2: the own-row term. An in-sample mechanism and a mechanism fitted on a separate draw have the same law. Their population terms are therefore equal in distribution. The mean paired difference on the same rows therefore estimates the mean of the empirical-process term. The table divides it by the SD of the in-sample DRTMLE fit.

paired difference

n = 1,000

4,000

16,000

own-row term of DR-TMLE

−2.30

−3.92

−4.10

own-row term with Q_r fitted on g_0

−1.82

−1.60

−0.98

own-row term of plain TMLE

−0.24

−0.01

+0.34

At n = 16,000 most of the own-row term acts through Q_r fitted on the in-sample g_n. The rest acts through the other steps, mainly equation (10).

In equation (10), g_{r,2} regresses (1_a − g_n)/g_n on Q̄_n. A least-squares fit with an intercept keeps the mean of its target. The mean of that target is −0.147, −0.062 and −0.023 on the training rows, and +0.253, +0.067 and +0.017 on fresh rows. Both means are zero at g_0. So equation (10) corrects in the wrong direction in sample.

Theorem 1’s Donsker condition is sufficient for this term to vanish, and a fit cannot check it. The measured term is consistent with its failure.

What this does not show. Plain TMLE stays within 0.42 SD for the ATE on law L. Its own leftover is first order when the outcome regression is wrong, so its interval is not established in this case either. On law L its parts nearly cancel. This page does not recommend plain TMLE.

Why no fix ships. A reduction on another index is a different estimator, and it needs its own proof. No fit can tell which case-table row it is in, so the status stays influence_curve, and no warning can separate the rows.

A parametric mechanism makes the interval conservative#

Take a logistic maximum-likelihood fit of g with the design X. Then g_n − g_0 ≈ g_0(1 − g_0)X'(β_n − β_0) and β_n − β_0 ≈ I^(−1)P_n S, with the score S = X(A − g_0). So R_{3,n} ≈ −c'I^(−1)P_n S, with c = P_0[F(1 − g_0)X]. In the outcome-wrong branch D_Y tends to zero, because g_{2,0,r} = 0 at g = g_0. Then:

Cov(D*, S)   = P_0[(1 − g_0)(Q̄_0 − Q̄)X]
Cov(D_A, S)  = P_0[Q̄_{0,r}(1 − g_0)X]
Cov(D^{*,#}, S) = c

The estimator’s curve is therefore D^{*,#} − c'I^(−1)S. That is the L_2 residual of D^{*,#} after its projection on the score span. Its variance is Var(D^{*,#}) − c'I^(−1)c, and the reported variance is Var(D^{*,#}). Arm 0 flips both signs, so the ATE curve is again a residual. Equation (9) moves g along Q_r/g, a function of g_n, so it adds second-order terms only.

fact

reason

the conservative case does not need a consistent reduction

D* − D_A(Q_r) has mean zero at every g in the model, for any fixed limit Q_r

cross-fitting gives the same projection

the fold scores average to the full-sample score: (1/V) Σ_v P_{n,−v} S = P_n S

the simultaneous band is conservative too

the reported covariance exceeds the true one by a positive semidefinite matrix. A symmetric convex set then has at least its nominal Gaussian probability (Anderson’s inequality)

The steps are standard: a linearization of the maximum-likelihood fit, a fixed-dimension stacked equation, and an L_2 projection. The derivation is this repository’s. In the probe, the in-sample SE ratio after the projection is 0.977 to 0.983 at n = 1,000 to 16,000. The cross-fitted cell has an SE ratio of 1.231 and a projected SE ratio of 1.047 at R = 400. In the registered study, the projected SE ratio is 0.994 in sample and 1.012 cross-fitted.

The bivariate reduction#

The bivariate reduction keeps Q_r, so its outcome branch is the one above. Its mechanism branch has the same linear structure. Appendix A, in the display of R_{5n} for that construction, gives R_{5n} = −P_0{(g_{0n,r} − g_{0,r})/g · (Q̄_n − Q̄_0)}, with g_{0n,r} = E_0[A | Q̄_n, Q̄_0, g]. That conditioning set includes g, so its H1 condition differs from the one above. The H1 column above is for the univariate reduction only.

The release claim#

The interval is valid when both nuisances are consistent at the product rates, under DR-TMLE’s own reduced-regression and solve conditions. With one nuisance inconsistent, the two extra equations remove the part of the first-order remainder that is a function of the consistent nuisance. The rest, R_{3,n} or R̃_{5,n}, can stay first order.

The one-wrong interval is valid for a declared known mechanism and conservative for a correctly specified parametric mechanism. With the mechanism wrong, the interval is not established, even for a correctly specified parametric outcome regression. It is also valid where the consistent estimate keeps the level sets of its truth, or where H1 holds. No fit can check the last two. A constructed level-set-breaking error produced a bias that grows with n in the registered study. On law L, one gradient-boosting mechanism with a wrong outcome regression produced a bias of +1.5 to +2.0 SD cross-fitted and −1.2 to −2.5 SD in sample (a data-adaptive mechanism).