Interaction terms and input replay in causal inference

August 27, 2026

"Recovering structure from data" covered the basics of causal inference: import a CSV, review candidate relationships, commit the ones worth keeping. Two more options have since shown up in that same review dialog, each extending what a committed model can represent rather than changing the workflow around it.

Interaction terms

Every relationship covered so far is a function of one column alone: rate × source, or a curved version of that if some nonlinearity is allowed. That's exactly right for a relationship that decomposes additively, one thing driving another, one thing decaying toward another, and it covers most everyday coupling with no loss of accuracy. It cannot represent a relationship whose effect depends on both variables together: predator-prey dynamics, mass-action chemistry, infection spread between two populations, anywhere the rate of change is a genuine product of two columns rather than a function of either alone. No amount of data fixes that; a source-only fit is structurally the wrong shape for it.

The column mapping step, with the interaction-terms checkbox visible and unchecked
Off by default: most systems don't need it, and a source-only fit is usually the right call when they don't.

The CSV behind the next two screenshots has exactly that shape: columnB's true rate of change is 0.8 × columnA × columnB, a pure product with no plain linear term standing in for it. With the checkbox left unchecked, causal inference still finds something, a linear approximation is often close enough to look plausible:

Candidate relationships with interaction terms off, a linear approximation
score 0.97: a reasonable fit for the wrong-shaped equation, not the real mechanism.

Checking it and running again, on the identical CSV, recovers the actual structure instead of an approximation of it:

The same candidates with interaction terms on, now including the real term
score 1.00, and the recovered interaction coefficient (0.79) lands close to the true generating value of 0.8.

The tag change matters more than the score bump: "includes interaction term" means this candidate now describes the real mechanism, one that would keep holding outside the range of this particular CSV, rather than a linear stand-in that happened to track it closely over this data. Leaving the checkbox off costs nothing on a system that doesn't need it, at most a little extra fitting time and occasionally one small extra term with a coefficient near zero. On one that does need it, it's the difference between recovering the relationship and missing it entirely.

Replaying recorded values for a column

A column nothing else predicts has always been a limited case: with no candidate edge and no self-term to explain it, it just sits at a constant value for the whole run. Any mapped column, not only one like that, can instead be marked to replay its own recorded values exactly.

The candidates review step scrolled to the new Inputs section
Any mapped column is eligible here, not only ones causal inference found no predictors for.

Importing this CSV without marking anything, columnA is an independent driver nothing in the data predicts, columnB responds to its previous value, and running the result for 5 seconds shows exactly that limitation:

The result after a plain import: columnA frozen at its starting value
columnA holds at 0.278854, its first recorded row, unmoving for the entire run.

Re-running the same import, this time checking columnA in the Inputs list before committing:

columnA checked in the Inputs list
Checking this supersedes whatever edge or self term would otherwise target the column, not add to it.

produces a genuinely different result, not just a different-looking one:

The result with columnA replaying its recorded trajectory
columnA reads -0.977038 at 5 seconds: the CSV's own recorded value at that exact row, not an approximation of it.

That's not a coincidence of this particular run: an input-replayed column reads its exact recorded value at every sampled instant, driven by a generated source term rather than a fitted equation, so it's correct regardless of how finely the simulation substeps. Checking it for a column drops whatever candidate edge or self-term used to target it, since Konjugate sums every contribution to a state additively and keeping both would double-count. This isn't limited to columns with no predictors either: a column with real fitted structure can still be held to its ground truth on purpose, to isolate one part of a system, to distrust a particular fit or as a clean baseline to compare the rest of the model against.

Where to go from here

Both of these extend the same review dialog "Recovering structure from data" introduced; nothing about importing, mapping columns or committing selected candidates has changed underneath them.

Follow Konjugate on LinkedIn for updates.

Comments