stan-dev / math

The Stan Math Library is a C++ template library for automatic differentiation of any order using forward, reverse, and mixed modes. It includes a range of built-in functions for probabilistic modeling, linear algebra, and equation solving.
https://mc-stan.org
BSD 3-Clause "New" or "Revised" License
723 stars 183 forks source link

Integrated Laplace approximation #3065

Open charlesm93 opened 1 month ago

charlesm93 commented 1 month ago

Description

Provide basic support for an integrated Laplace approximation.

The motivation is to handle hierarchical models with a latent Gaussian model of the form $\eta \sim p(\eta)$ $\theta \sim \text{normal}(0, K(\eta))$ $y \sim p(y \mid \theta, \eta)$. We construct a Laplace approximation of $p(\theta \mid \eta, y)$ by matching the mode and curvature, and then obtain an approximation of the log marginal likelihood $\log p(y \mid \eta)$.

A call to the function may look as follows:

target += laplace_marginal(theta0, ll_fn, ..., K_fn, ...);

where

We can also give the user control over the underlying Newton solver.

target += laplace_marginal_tol(theta0, tolerance, max_num_steps, hessian_block_size, solver, max_step_linesearch, ll_fn, ..., K_fn, ...);

The additional arguments are:

Going the other way, we can also provide a simplified interface where the likelihood is not user specified but set ahead of time.

target += laplace_marginal_poisson_log(theta0, *, K_fn, ...);

where * is a place-holder for arguments specific to the Poisson likelihood with a log link.

Next, we need to specify an rng function to recover draws from $p(\theta \mid \eta, y)$. In practice, we may also want "out-of-sample" draws, in which case we would evaluate $\theta$ for a different set of values passed to $K$ (think GP process). The call for the functions would be:

vector[nObs] theta = laplace_marginal_rng(theta0, ll_fn, ..., K_fn, ...);

vector[nObs_pred] theta_pred = laplace_marginal_pred_rng(theta0, ll_fn, ..., K_fn, ..., ...);

where for the second function, we pass in two sets of inputs for K_fn. As before, we can wrap these functions for a specific likelihood, and also give users control over the underlying Newton solver.

One thing to note is that under-the-hood, the autodiff uses higher-order derivatives and so the fwd mode must be supported.

There may be other features worth supporting, but for now, we can start here (and even split this into multiple PRs).

This issue replaces #755.

References

Current Version:

v4.8.1

charlesm93 commented 1 month ago

@SteveBronder @WardBrian @avehtari

avehtari commented 1 month ago

Next, we need to specify an rng function to recover draws from . In practice, we may also want "out-of-sample" draws, in which case we would evaluate for a different set of values passed to (think GP process). The call for the functions would be:

It would be good to clarify that here the prediction is not for $y$

There may be other features worth supporting, but for now, we can start here (and even split this into multiple PRs).

It would be useful to have a function returning the mean and sd, so that these not need to be estimated from rngs

tuple(vector, vector) theta_mu_sigma = laplace_marginal_mean_sd(...)

and a corresponding one for out-of-sample

dpsimpson commented 1 month ago

So excited to see this happening again