# 1. What Is Marketing Mix Modeling
Marketing Mix Modeling (MMM) estimates the impact that different marketing channels — TV, search, social, display, and so on — have on a business outcome like sales, conversions, or revenue, using historical, aggregated spend and performance data rather than user-level tracking. This makes it especially valuable in a privacy-regulated environment where user-level attribution (tracking an individual user's journey across channels) is increasingly restricted: MMM works entirely from aggregated data, so it doesn't depend on cookies, device IDs, or cross-platform user matching. The output of an MMM is typically a set of channel-level contributions and ROI estimates that inform how a marketing budget should be allocated across channels.
# 2. Building an MMM Model
## 2.1 Step 1: Fit a baseline regression model
The starting point for any MMM is a baseline regression model, commonly fit in Python using `from statsmodels.formula import api as smf` to specify a custom formula and fit an OLS model. Before drawing any inference from it, it's essential to confirm the model is reasonably well-fit: check the standard regression assumptions, look for an $R^2$ of at least 0.6–0.7, and confirm the cross-validation score is decent. Only once the baseline model clears these checks does it make sense to interpret its coefficients.
From the fitted model, each channel's **contribution** to the outcome can be calculated in three steps:
$unweighted\text{-}contribution = actual\text{-}spend \times coef$
$weight = \frac{unweighted\text{-}contribution}{\sum{unweighted\text{-}contribution}}$
$weighted\text{-}contribution = weight \times actual\text{-}target$
In words: multiplying each channel's spend by its regression coefficient gives a raw, unweighted sense of how much that channel is contributing; dividing each channel's unweighted contribution by the sum across all channels converts that into a share (weight) of total contribution; and multiplying that share by the actual observed target value rescales each channel's contribution back onto the same scale as the real outcome, so the contributions from all channels sum to the actual total.
## 2.2 Step 2: Add saturation
Marketing channels rarely respond to spend in a straight line — most experience **diminishing returns** as spend increases, and some experience delayed or threshold effects before they kick in at all. The saturation function in an MMM is meant to capture exactly this: how a channel's incremental response behaves as spend increases.
**Selecting a saturation curve.** A good starting point is to visualize the relationship between spend and outcome for each channel and evaluate whether it shows linear growth, fast diminishing returns, or a threshold effect. Simpler, easily measurable channels like branded search often fit **logarithmic or exponential** saturation curves well, while awareness-driving, upper-funnel channels such as TV are often better modeled with **Hill or Sigmoid curves**, since those functional forms can capture delayed scaling followed by eventual saturation. In practice, the final choice should be based on comparing model fit, coefficient stability, interpretability, and how well the resulting curve matches real-world business intuition — not fit alone.
![[Pasted image 20260610093713.png|338]]
To operationalize this, spend data is transformed using one of several standard functional forms:
- **Log transformation** (aggressive saturation): `np.log1p(spend)`.
- **Root transformation** (mild saturation): `np.sqrt(spend)`.
- **Exponential transformation**: $f(x)=1-e^{-\lambda x}$, where a small $\lambda$ produces slow saturation. A reasonable starting point for $\lambda$ is `1 / df[spend].median()`. This form is simple, has only one parameter to fit, is stable, and is easy to explain to stakeholders — but it cannot represent an S-shaped (delayed-then-accelerating) response curve.
![[Pasted image 20260610100239.png|301]]
- **Hill transformation**: more aggressive and flexible than the exponential form, capable of modeling a full S-curve, and considered an industry-standard functional form for MMM: $f(x) = \frac{x^\alpha}{x^\alpha+\theta^\alpha}$.
- **Michaelis-Menten transformation**: a special case of the Hill transformation where $\alpha=1$: $f(x) = \frac{x}{x+\theta}$.
![[Pasted image 20260610095406.png|347]]
## 2.3 Step 3: Add adstock effect
Marketing spend rarely has an effect only in the period it's spent — a TV ad seen this week can still be influencing purchase decisions weeks later. **Adstock** models this carryover effect.
**Selecting an adstock function.** The **geometric adstock** function models carryover as simple exponential decay, where each period retains a fixed percentage of the previous period's effect:
$
Adstock_t = Spend_t + \lambda \times Adstock_{t-1}
$
For example, $\lambda = 0.7$ means 70% of a period's adstock carries over into the next period. Geometric adstock is simple, interpretable, and stable, but it cannot represent a delayed peak in impact — it's best suited to "short-memory" channels whose effect decays steadily from the moment of spend.
The **Weibull adstock** function is more flexible: it can model both fast and slow decay, as well as a delayed peak effect, which makes it a better fit for upper-funnel or offline channels whose impact often builds before it fades.
**Delayed adstock** adds an explicit lag before a channel's strongest impact occurs, useful for channels where the effect doesn't peak immediately.
**Setting a prior on the adstock decay rate.** In a Bayesian MMM (see §4), the decay rate $\lambda$ is typically given a weakly informative prior centered on domain knowledge — for instance, TV is known to decay more slowly than display, so its prior might be centered in the 0.3–0.7 range. Prior predictive checks (simulating from the prior before touching the actual data) should be used to confirm the chosen prior produces plausible-looking sales curves before fitting the model.
# 3. Choosing a Model Family for MMM
Several regression families are commonly used to fit an MMM, and the right choice depends on how correlated the channels are and whether feature selection is needed:
- **OLS**: simple and easy to interpret, but can produce unstable coefficients when channels are highly correlated.
- **Ridge (L2)**: shrinks coefficients toward zero and specifically helps handle multicollinearity between channels, without dropping any of them.
- **Lasso (L1)**: shrinks coefficients and can push some to exactly zero, effectively performing feature selection among the candidate channels and controls.
- **ElasticNet**: combines L1 and L2 penalties, balancing multicollinearity handling with feature selection.
# 4. Bayesian MMM
Bayesian Marketing Mix Modeling estimates the impact of marketing channels on a business outcome using Bayesian statistics rather than traditional (frequentist) regression. The key difference is that Bayesian MMM estimates a full **probability distribution** for each parameter instead of a single point estimate — so instead of concluding "TV ROI = 1.5," a Bayesian MMM would report that TV ROI is likely around 1.5, with a 95% credible interval of, say, [1.1, 1.9], explicitly modeling the uncertainty around that estimate.
**Why marketing data specifically benefits from a Bayesian approach.** Marketing data presents several recurring challenges: channels are often highly correlated because they launch together as part of the same campaign (TV, YouTube, and Search often ramp up simultaneously), and Bayesian methods handle this multicollinearity better than traditional regression. Marketing data also tends to be noisy, and business decisions built on it require understanding the uncertainty around an estimate, not just the point estimate itself. On top of that, privacy regulations increasingly limit user-level attribution, making aggregated, probabilistic modeling more important than ever. Finally, Bayesian MMM can incorporate prior business understanding directly into the model, whereas traditional MMM uses no such prior information. Bayesian MMM addresses all of these challenges at once by incorporating prior knowledge and explicitly modeling uncertainty throughout.
**Prior, likelihood, and posterior in this context.** The **prior** represents existing knowledge before observing the current data — for example, the belief that search advertising usually has a positive effect, or that TV ROI is typically between 1 and 3 — encoded as probability distributions. The **likelihood** represents the probability of observing the collected marketing data given a particular set of model parameters. The **posterior** combines the prior with the observed data, following $Posterior \propto Likelihood \times Prior$, and it's this posterior distribution that Bayesian MMM ultimately reports.
**Google's Meridian** is a modern, open-source Bayesian MMM framework designed to estimate incremental channel contribution, estimate both ROI and marginal ROI, optimize budget allocation, work with aggregated, privacy-safe marketing data, and perform causal inference without relying on user-level tracking. It combines Bayesian inference with modern causal modeling techniques to produce more robust marketing measurements than a traditional frequentist MMM.
**Diagnosing a Bayesian MMM.** Because Bayesian models are typically fit using Markov Chain Monte Carlo (MCMC), with multiple chains run in parallel, the standard diagnostic is $\hat{R}$ (R-hat), which measures whether all the chains converged to the same posterior distribution by comparing between-chain variance to within-chain variance. R-hat should always be checked before interpreting any model results.
| $\hat{R}$ | interpretation |
| ----------- | ------------------------------------ |
| $\approx 1$ | excellent convergence |
|
lt;1.05$ | acceptable |
| gt;1.1$ | poor convergence, results unreliable |
Beyond R-hat, it's worth reviewing whether the posterior distributions themselves are reasonable, sufficiently narrow, and aligned with domain knowledge — wide credible intervals are a sign of high uncertainty in the estimate. Model stability should also be checked by comparing training vs. testing $R^2$ and training vs. testing MAE; a large gap between the two suggests overfitting. Finally, rather than relying on a random train/test split, MMM is best validated with **rolling time-series validation**, which evaluates the model's performance by having it forecast genuinely future periods rather than randomly held-out ones. **PyMC** is a commonly used library for fitting Bayesian MMMs in Python.
# 5. Validating an MMM
A trustworthy MMM needs to be validated on several fronts, not just checked for a good in-sample fit:
- **Data quality**: confirm the underlying spend and outcome data is clean and complete before trusting any model built on it.
- **Time-based split and cross-validation**: evaluate the model on genuinely future time periods, not randomly shuffled ones, since marketing data is inherently sequential.
- **Residual analysis**: residuals should be centered around zero, show no clear pattern over time, and have relatively stable variance.
- **Stability metrics**: track $R^2$, mean absolute error (MAE), and root mean squared error (RMSE) for both the training and test data, and look for reasonably narrow confidence intervals around the estimates. Common causes of model instability include multicollinearity between channels, too many features relative to the amount of data (which risks overfitting, especially for tree-based models), missing adstock or saturation transformations, and simply having too few observations.
- **Comparison with business intuition**: channel coefficients and ROI estimates should make sense to people who understand the business, not just fit the data well statistically.
- **Validation against real experiments**: where possible, compare the MMM's estimated effects against results from controlled experiments, such as A/B tests or geo-based holdout tests.
**How do you know your MMM isn't just fitting to noise?** Run an out-of-sample backtest on a held-out time period rather than trusting in-sample fit alone. Check that channel coefficients remain reasonably stable across different time windows — a coefficient that swings wildly depending on which period you fit is not to be trusted. And decompose the fitted values against the actual outcome to confirm the residuals behave like white noise rather than showing autocorrelation, which would indicate the model is systematically missing some pattern in the data.
# 6. Common MMM Challenges
**Highly correlated marketing channels.** When channels like TV, YouTube, and Display all launch simultaneously, their spend patterns become correlated by construction, which produces unstable coefficients, inflated uncertainty, and sometimes even negative ROI estimates that don't make business sense. Reasonable responses include switching to a Bayesian MMM, using Ridge regression, applying informative priors, constraining coefficients to plausible ranges, and validating with lift experiments.
**Negative media coefficients.** A negative coefficient on a media channel does not automatically mean that channel is hurting performance. Common underlying causes include multicollinearity, missing control variables, poorly chosen adstock or saturation transformations, unmodeled seasonality, and promotions or holidays that weren't included in the model. These possibilities should be investigated before modifying or removing the channel from the model.
**Large spending spikes.** Occasional campaign bursts can distort coefficient estimates. It's worth verifying whether a spike reflects a genuine campaign or a data quality issue, making sure the model's saturation curves are actually capturing diminishing returns at high spend, and generally avoiding the temptation to overreact to a single temporary spend increase.
**Noisy daily data.** Daily marketing data tends to contain substantial random noise. Aggregating to a weekly level is frequently preferred, since it reduces random fluctuations, improves the signal-to-noise ratio, and produces more stable parameter estimates overall.
**Handling multicollinearity between channels.** Channels that run simultaneously are correlated by construction, which is exactly the kind of problem Bayesian priors help with — they regularize coefficients toward zero and prevent overfitting to the correlated spend patterns. When the model spans multiple markets, hierarchical priors can be used to share information across markets while still allowing each one its own estimate.
# 7. Why Prediction Accuracy Isn't Everything
A model with the lowest prediction error is not necessarily the best marketing model. For MMM specifically, interpretability and stability are often more important than squeezing out a small improvement in predictive accuracy, since the whole point of the model is to inform real budget decisions that stakeholders need to trust and understand.
# 8. When Marketing Disagrees With the Model
Disagreement between the model's output and marketing stakeholders' intuition should be treated as an opportunity to improve the model, not as a reason to dismiss either side outright. A reasonable approach is to: first understand exactly why stakeholders disagree; validate the modeling assumptions that led to the disputed result; check the underlying data quality; look for missing variables such as promotions, holidays, pricing changes, other campaigns, or competitor activity that the model might not be accounting for; compare the model's results against controlled experiments like A/B tests or geo experiments; explain the uncertainty in the estimate using credible intervals rather than presenting a single number as fact; and iterate with stakeholders to refine the model based on what's learned.
# 9. Budget Allocation Recommendations
A typical budget-optimization workflow built on top of a fitted MMM follows four steps:
1. **Rank channels by ROI** to identify which channels are generating the highest return on investment.
2. **Account for saturation.** Simply pouring more budget into the highest-ROI channel is a mistake, because every channel eventually experiences diminishing returns. Instead, evaluate each channel's **marginal ROI** — the additional return generated by one more unit of spend at the current spend level — and allocate incremental budget toward whichever channel has the highest marginal ROI, not necessarily the highest average ROI.
3. **Simulate budget scenarios**, such as increasing Search spend by 20%, reducing TV spend by 10%, or shifting Display budget into Paid Social, and estimate the expected business outcome under each scenario.
4. **Recommend a reallocation** using the model's outputs to identify the allocation that maximizes expected business outcomes, while explicitly accounting for both diminishing returns and the uncertainty in the underlying estimates.
# 10. Appendix
- [Project](https://colab.research.google.com/drive/1kUFYUw3NFAQFsmj8SThU9y1pnyLbv1PA#scrollTo=T17yqPxa0Jkz)