Skip to main content

modeling.model()

Parse a specification and compile a Bayesian path model.

Usage

modeling.model(
    spec_string,
    data=None,
    families=None,
    panel=None,
    pooling=None,
    latent=None,
    priors=None,
    scaling=None,
    *,
    initial=None,
    _initial_internal=None,
    **kwargs
)

When data is None, returns a data-free model suitable for DAG exploration: graph(), equations(), priors(), and all identification helpers work immediately. Methods that require data (fit(), do(), design(), etc.) raise RuntimeError with an actionable message.

Parameters

spec_string: str

Model specification in the pathmc DSL.

data: IntoFrame | None = None

Observed data as a pandas or polars DataFrame. When None, the model is created in data-free mode for DAG exploration and identification.

families: dict[str, str] | None = None

Per-variable distribution families (default "gaussian").

panel: dict[str, str] | None = None

Panel structure with "unit" and "time" keys mapping to column names. Activates panel mode. Convolution adstock compiled without it treats row order as one series and warns.

pooling: str | dict | None = None

"partial" for random intercepts per unit. A dict like {"intercept": True, "slopes": ["var"]} enables random slopes. An optional "by_var" entry adds structured pooling: a dict mapping predictor names to {"coefficient": dims} (dims name panel['unit'] columns to pool over, emitting hyperpriors mu_{var}_{dim} / sigma_{var}_{dim}) or to the bare string "none" (unpooled per-cell parameters, including transform parameters such as adstock decay). None (default) means complete pooling (cross-sectional).

latent: list[str] | None = None

Variables to treat as latent deterministic mediators. These must appear as LHS of a regression but need not have a data column. The model compiles without a likelihood for these variables.

priors: dict[str, Prior] | None = None

Custom prior specifications mapping parameter names to Prior objects from pymc_extras. Only the specified parameters are overridden; all others use sensible defaults. Call .equations() on the returned model to see all parameter names.

Examples

:
from pymc_extras.prior import Prior

m = pathmc.model(
    spec,
    data,
    priors={"beta_Y": Prior("Normal", mu=0, sigma=2)},
)
scaling: pathmc.Scaling | ScalingFactors | None = None

Scale heterogeneous columns onto a common internal scale before compilation, so default priors stay calibrated across units of different magnitude. Scaling.target configures endogenous (outcome) columns and Scaling.channel exogenous (predictor) columns; see pathmc.Scaling for the spec format. The fitted factors are stored on the returned model as fitted_scaling.

User
surgery
outputs
business
columns
initial: Mapping[str, Any] | None = None

Pre-sample state for every observed lag() base, in business units. A key is the base variable named by lag(), not a generated column. A value is a finite number broadcast to every fitted unit, or a mapping of exactly the fitted unit labels. These values are the state immediately before the first fitted time — not the first observed row, and not an extra outcome period. None keeps the legacy fill: an endogenous base uses that unit’s first observed value; an exogenous base uses a <variable>_lag1 column when present, otherwise the first observed row, otherwise zeros. Explicit values replace that fill for fitting and for do(). Latent lag bases stay on their init_{variable} prior. The normalized model-unit record is PathModel.initial_baseline.

_initial_internal: Mapping[str, np.ndarray] | None = None
Private. Refit passes already-normalized model-unit arrays when the working frame is already scaled. Do not combine with initial=.

Returns

PathModel
Compiled model ready for inspection and fitting, or a data-free model for exploration when data is None.

Raises

ValueError

If a latent variable is not endogenous, or an observed endogenous variable is missing from data.

NotImplementedError
If a directed edge lies inside a ~~ block (Y2 ~ Y1 together with Y1 ~~ Y2). Drop the within-block path or the ~~ clause. The same refusal applies with or without data.