Duplicate-edge dedup + opt-in catalyst bundling#46
Merged
Conversation
Distinct virtual reactions of one curated reaction can canonicalize (union-find) to the same target node; a catalyst/regulator attached to each then produces exact-duplicate rows (same source, target, sign, type, reaction). The solver has no dedup — create_reaction_from_edges pushes each edge's parent into `activators` — so a duplicated catalyst is double-weighted in the activator aggregation (geomean/hill), skewing the reaction toward that parent. Add a final dedup pass on the edge list keyed by (source, target, pos_neg, and_or, edge_type, edge_reaction_id). Distinct reactions keep distinct edge_reaction_id, so only truly-redundant rows collapse. Scale: 39 of 92 catalog pathways affected; Pre-NOTCH 40,548 -> 27,552 edges (32% were duplicates), FGFR2 -7,806, ERBB2 -3,345, RAF -2,191. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…nit shatter) Catalysts and positive regulators were decomposed to their individual subunit proteins, making each protein a SHARED node wired directly to every reaction its complexes catalyse — a super-hub that lets signal flood unrelated reactions and is inconsistent with the complex-as-node treatment of reaction inputs. Now they use bundle_complex mode in _decompose_regulator_entity: a complex is ONE node regardless of internal sets (no subunit shatter, and no cartesian set-variant expansion either — variant expansion blew TP53 up to 156k edges). Only genuine top-level "one-of" EntitySets still expand into OR alternatives. Negative regulators keep variant decomposition as before. Env toggle LNG_CATALYST_SUBUNITS=1 restores the old subunit shatter for A/B. Effect (TP53): 18,082 -> 5,631 edges (69% fewer) — its transcription catalysts were heavily shattered. (Does NOT by itself fix DAXX over-reach, which is network-wide shared-node coupling + undamped propagation, a separate issue.) Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
…_CATALYST_BUNDLE Catalyst/positive-regulator bundling (the faithful complex-as-node representation) is more correct but OFF BY DEFAULT: it exposes a pre-existing UUID-silo defect (a complex produced by one reaction and catalysing/regulating another is stored as separate, un-unified nodes — compounded by set-variant mismatches and non-deterministic set-member selection), so the curated produce→catalyse chain doesn't carry signal. Subunit decomposition accidentally masks this via spurious shared-protein hub paths and scores ~1.2pp higher on the experimental set — not because it's more correct, but because the hubs reconnect what the silo severs. Until the silo × set-variant entity-identity problem is redesigned, subunit decomposition remains the default; bundling is opt-in via LNG_CATALYST_BUNDLE=1 for when that work happens. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
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.
Follow-up to #45 (which merged the set-expansion fix). These commits were made after #45 merged and never reached main.
Ships by default
Drop fully-identical duplicate edges — distinct virtual reactions of one curated reaction can canonicalize to the same target node; a catalyst/regulator attached to each then produces exact-duplicate rows that the solver double-weights in its activator aggregation. Final dedup keyed by (source, target, sign, type, reaction). 39/92 catalog pathways affected; Pre-NOTCH 40,548→27,552 edges (−32%), FGFR2 −7,806, ERBB2 −3,345. Benchmarked neutral (experimental 66.43%, curator 81.18%).
Behind a toggle, OFF by default (
LNG_CATALYST_BUNDLE=1)Catalyst/regulator bundling — the faithful complex-as-node representation (no subunit shatter). Kept opt-in because it exposes a pre-existing UUID-silo defect (a complex produced by one reaction and catalysing/regulating another is stored as separate un-unified nodes, compounded by set-variant mismatch + non-deterministic set-member selection) that breaks the curated produce→catalyse chain. Subunit decomposition accidentally masks this via spurious hub paths and scores ~1.2pp higher on experimental — luck, not correctness. Default stays subunit until the canonical entity-node unification is redesigned (documented ceiling; full-merge was −204pp).
Net effect at default settings: dedup only; bundle inert unless toggled.
Full non-DB suite (139) green, ruff + mypy clean, coverage 46%.
🤖 Generated with Claude Code