Repository navigation
Conversation
_eitc_source_decomposition_total_for_bounds summed every Table 2.5 by-children row inside the uprating group. For the all-AGI group that is each split's 28 AGI bins and its total row, so the source EITC was counted twice and the four all-AGI total rows compiled at half their value (factors 0.5209 amount, 0.4877 returns on the pinned feed). Count only each split's outermost contained rows, and refuse a split whose AGI rows cross. Adds example tests, Hypothesis properties over synthetic decompositions (conservation, child-split preservation, totals equal their bins under uniform growth) and a pinned-feed check. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Doubling the eight Table 2.5 EITC child total rows moves the pinned-feed national_state registry from e1f9906bf0e0 to 3fad14f85468 (full: f5bd921d6b21 to c3aaea9c1e8c). Target counts are unchanged: 33,250 compiled, 6,102 national_state. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
After #1227 each Table 2.5 child split's all-AGI total row keeps the TY2023 all-AGI child mix while each AGI bin keeps its group's, so on the pinned feed a split's total row and the sum of its 28 bins differed by up to 16% (childless amount 1.157), and calibration saw both. _rake_eitc_child_splits now rakes each decomposition's child x AGI-group matrix of source bins (iterative proportional fitting) to the splits' uprated total rows and the active filing-season AGI groups. Total rows keep their values; the 224 bins move by x0.857-1.226; every split's bins sum to its total row and every AGI group's bins to its active EITC. Decompositions with nothing to reconcile (no total rows, or uprated on the all-returns total) keep their per-row factors. Evidence (experiments/eitc-child-split-rake-20261012/): no TY2024 child mix is published; on published Table 2.5 TY2013-2023 keeping the all-AGI mix predicted next year's split totals with 40-70% of the bins' error (the bins under-predicted childless EITC in every clean year pair); it sits 3-4x closer to the HT2 state EITC-by-children rows on the same surface; and SOI's full-population TY2023 state data confirm the TY2023 mix it keeps. national_state stays at 6,102 targets, version 3fad14f85468 -> 31bd18096d33; full stays at 33,250, c3aaea9c1e8c -> ac32014f3325. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…#1235 review) Round 1 of the independent review found two majors. A group with no EITC in either year made the per-row uprating fall back to the all-returns total for its bins, and the plan's per-row index check then skipped the whole rake. And plain IPF capped at 10,000 sweeps refused feasible, ill-conditioned margins. - _eitc_rake_plan decides from structure: one all-AGI total row per split, leaf bins tiling AGI, and an AGI group for the totals and every bin. An empty group takes a zero factor; a group with active EITC but no source EITC is refused. - _rake_two_margins checks exactly whether a positive scaling exists (Menon/Brualdi) and refuses with a specific message if not. It then finds the IPF solution by damped Newton steps on the convex dual, pinning each block's largest column with a Jacobi-scaled solve, and finishes with exact IPF sweeps. Rows hold to rounding, columns to 1e-12. - The bin adjustment is relative to the recorded per-row group factor, so it stays consistent beside rounded published subtotals. - The per-row AGI metadata moves into _eitc_agi_uprating_metadata, unchanged for #1227's rows. - The plan uses an _EitcRow NamedTuple and the solver annotates its nested functions; the spine-blindness check had failed on lambda row: row[1:]. - New tests: the review's counterexamples, the empty and refused groups, the rounded-subtotal adjustment, a Hypothesis property against a scipy linprog feasibility oracle, and positive seeds spanning ten orders of magnitude. - Experiments: option (b) records the factor its new total implies; results regenerated; README separates pairs from runs, qualifies the level gap (TY2018 amount) and states the bin-level tradeoff. national_state 31bd18096d33 -> 1aafec44dbfa (values move in the last bits; the adjustment metadata changed); full ac32014f3325 -> ec807d77a746. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…d 2) Round 2 found the feasibility check's rounding tolerance taking strict slack below 1e-12 of the total for an exact (infeasible) fill, so it refused a feasible decomposition. It now refuses only what is certain for the margins as given: an excess beyond rounding, or an exact fill that other splits also reach. Margins within rounding of the boundary go to the solver. Also from round 2: - The Newton solve falls back to Levenberg-Marquardt damping when rounding makes the system singular (a 1e16 dynamic range), and the seed is normalized by its largest cell before summing (1e308 cells). - Feasibility is checked over subsets of the shorter side; more than 16 splits and 16 groups is refused rather than left unchecked. - A published row over an AGI group that is zero although a bin inside it is not is refused: no factor the uprating records for it would be true. New tests: the round-2 counterexamples, direct and through the compiler. national_state 1aafec44dbfa -> f96aac657fa6 and full ec807d77a746 -> cb0eaa0418f2 (values move in the last bits); results regenerated. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This was referenced Oct 14, 2026
Contributor
Author
|
A source anomaly that bears on this rake. IRS's own TY2023 Table 2.5 (
Context: microcosm#1274, which adds CI tests on the real TY2023 rows after #1227. 🤖 Generated with Claude Code |
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Depends on #1227. This branch sits on #1227's head (f44d26e), so until #1227 merges the diff also shows its two commits. This PR's own change is the last commit.
Methodology call for Max. No published source decides between the options below, so this is queued as a decision rather than merged on the usual gates. The recommendation, option (c), is implemented here and ready to merge. Options (b) and (d) are each a few lines if preferred.
What is inconsistent after #1227
_uprate_cross_period_eitc_decompositionsscales the TY2023 SOI Table 2.5 EITC-by-AGI-and-children rows to the TY2024 filing-season EITC by AGI:The AGI groups grew at different rates (amount ×0.85 at $5,000–$10,000 to ×1.73 at $50,000 and over; returns ×0.81 to ×1.38). So per split, the total row and the sum of its 28 bins disagree, and both levels sit on national_state and full:
The options, on the pinned feed
These are release-equivalent compiles of
consumer_facts_us_51aa40f.jsonl, fromexperiments/eitc-child-split-rake-20261012/results/.Why (c)
24in25ic.xlsreturns 404.Full write-up:
experiments/eitc-child-split-rake-20261012/README.md.The change
_rake_eitc_child_splitsruns after the per-row uprating. For each decomposition (kind, source period, target period), it builds the child-split × AGI-group matrix of source bins (_eitc_rake_plan) and scales it (_rake_two_margins) to the splits' uprated total rows and the active AGI groups._rake_two_marginsfinds the IPF solution: the unique positive scaling r_i·s_j·x_ij that meets both margins and keeps every cross-product ratio of the source._require_scalable, the Menon 1968 / Brualdi 1968 condition, over subsets of the shorter side, at most 16) and refuses only when the margins are certainly infeasible: an excess beyond rounding, or an exact fill that other splits also reach. Margins within rounding of the boundary go to the solver.When it rakes. A decomposition is raked when:
Otherwise it keeps its per-row factors: uprated on the all-returns total, every row already has one factor, and with no total row there is nothing to reconcile to. A group with no EITC in either year takes a zero factor.
Refusals (
ValueError):Metadata.
uprating_reconciliation: two_margin_rake.uprating_factor(its effective factor),uprating_agi_group_factor(the factor the per-row uprating recorded) anduprating_child_split_adjustment. The adjustment is relative to the recorded factor, so the group factor times the adjustment equals the bin's factor.Refactor. The per-row AGI metadata moved into
_eitc_agi_uprating_metadata, with no change for Count each EITC child split once in the Table 2.5 uprating source total #1227's rows.Invariants
These hold for every decomposition the rake applies to:
_rake_two_marginssucceeds exactly when a positive scaling exists.Tests
test_us_eitc_decomposition_uprating.py(36 tests)._rake_two_marginsrefusals;compile_us_fiscal_target_registry;scipy.optimize.linprogoracle (the largest t such that some matrix on the seed's support, every positive cell ≥ t, meets both margins). It also checks margins and cross-product ratios;_rake_two_marginsagainst the closed-form 2×2 solution (bisection on the cross-product ratio).test_us_fiscal_targets.py.test_pinned_feed_eitc_child_split_bins_sum_to_their_total_rows: per split Σ bins = total row; per active group Σ bins = the group's EITC; adjustments within 0.85–1.23.test_us_eitc_decomposition_uprating.py: 36 passed;test_us_fiscal_targets.pyandtest_us_fiscal_refresh_builder.pywith-k "eitc or pinned_feed or decomposition": 25 passed;test_us_spine_blindness.py: 498 passed. Round 1's CI failed this static check onlambda row: row[1:].Separate findings, not changed here
23in55cmcsv.csv, with EITC by children) are not yet in the pinned feed; Add IRS SOI Historic Table 2 TY2023 national, state broad and state EITC facts chronicle#295 is adding them. Their child mix sits 0.19–0.24 pp TVD from (c), so they would widen the gap to (b) and (d).Review
subfleet run --task review --tier hard, head a2a529d): REQUEST_CHANGES.axiom: n/a: target-compilation methodology for calibration targets (no policy encoding)
🤖 Generated with Claude Code