skip to content

A rejection sampler for a truncated normal accepts only 3% of proposals; why?

level: seniorimportance: should knowfreq 34%

answer

  1. compare the envelope's area with the target's
  2. the accept rule is a ratio of densities
  3. acceptance probability is exactly one over M
  4. M is proposals needed per accepted draw
  5. a flat box over a tail wastes draws

basics

~20 s

The envelope is far too loose. Rejection sampling accepts a proposal with probability 1/M, where M is how much the envelope must be inflated to cover the target, so a box dwarfing the truncated region wastes nearly every draw. Accepted draws remain exact.

solid answer

~50 s

Rejection sampling draws a candidate from a proposal density `g`, then accepts it with probability `f(x)/(M*g(x))`, where `M` satisfies `f(x) <= M*g(x)` everywhere. The overall acceptance probability is exactly `1/M`, so `M` is also the expected number of proposals per accepted draw. A 3% rate means `M` is around 33: the envelope encloses roughly 33 times the area the target occupies. With a uniform box over a truncated normal, that happens when the retained interval sits far out in the tail, where the density is tiny relative to the box height set near the peak. The fix is a tighter envelope, not more compute: reshape the proposal to follow the target, or sidestep rejection entirely by inverting the truncated CDF, which maps a uniform onto the interval and accepts every draw. Crucially, the low rate costs time only. Accepted draws follow the target exactly.

go deeper

for a junior

Recall the three steps: propose from an easy distribution, draw a uniform, accept when it falls under the density ratio. Know that rejected candidates are simply thrown away.

for a middle

Derive that the acceptance probability is exactly one over M and explain the geometric picture of throwing points uniformly under a blanket and keeping those beneath the target curve.

for a senior

Diagnose from the measured acceptance rate: read off M, identify the envelope mismatch causing it, and choose between a tighter proposal, a piecewise envelope, or the inverse-CDF route. Confirm the sample is still unbiased.

for a principal

Own the build-versus-buy call on sampling machinery. Decide when a hand-rolled rejection sampler is a maintainable choice and when its dimensional limits mean the team should restructure the problem instead.

## How rejection sampling works You want draws from a density `f` that you can evaluate but not invert. Choose a proposal density `g` you can sample easily, and a constant `M` with `f(x) <= M*g(x)` for every `x`. Then repeat: 1. Draw a candidate `X` from `g`. 2. Draw `U` from Uniform(0,1). 3. Accept `X` if `U <= f(X) / (M*g(X))`; otherwise discard it and start again. The accepted values are exact draws from `f`. The geometric picture is the cleanest way to hold it: the curve `M*g` is a blanket lying over the curve `f`. You throw points uniformly under the blanket and keep only those that also fall under `f`. Points uniform under a density's curve have that density as their horizontal marginal, which is why the survivors are distributed as `f`. ## Where the acceptance rate comes from Averaging the acceptance probability over the proposal gives P(accept) = integral of g(x) * f(x)/(M*g(x)) dx = (1/M) * integral of f(x) dx = 1/M since `f` integrates to 1. So the acceptance rate is `1/M` exactly, and the number of proposals needed per accepted draw is geometric with mean `M`. Reading it as areas: acceptance equals the area under `f` divided by the area under the blanket. A blanket 33 times too big yields a 3% rate. ## Why a truncated normal punishes a box envelope A truncated normal restricts a normal to an interval `[a, b]` and renormalises. The simplest envelope is a uniform box over `[a, b]` whose height is the maximum of the density on that interval. When `[a, b]` straddles the peak, the density fills a decent share of the box and the rate is respectable. When `[a, b]` sits out in a tail, say from 2.5 standard deviations upward, the density at the left edge dwarfs the density at the right edge, so the box height is set by the edge value while most of the box sits over near-zero density. The ratio of areas collapses and the sampler grinds. The same failure appears whenever the envelope's shape does not track the target's shape: a heavy-tailed proposal over a concentrated target, or a wide proposal over a sharply peaked one. ## Diagnosing and fixing it Measure the empirical acceptance rate first; it estimates `1/M` directly and tells you how much waste there is. Then: - **Tighten the envelope.** Use a proposal whose shape follows the target rather than a flat box. For a tail region of a normal, a shifted exponential envelope tracks the decay and lifts acceptance dramatically. - **Lower M to the true bound.** A conservative `M` chosen "to be safe" costs proportionally. `M` should be the smallest constant for which the inequality still holds everywhere, since acceptance is exactly `1/M`. - **Split the region.** Piecewise envelopes over sub-intervals fit far more tightly than one global blanket. - **Avoid rejection altogether.** For a truncated distribution with an invertible CDF the inverse-transform route is exact and wastes nothing: map a uniform onto the retained probability range, `X = F^-1(F(a) + U*(F(b) - F(a)))`, and every draw is accepted. ## The bias question A low acceptance rate is a cost, not a correctness problem. Provided the envelope really does dominate the target everywhere, accepted draws are exactly distributed as `f` regardless of how many were rejected. Three ways to convert the cost into a genuine bias, all of which show up in real code: - **A broken bound.** If `f(x) > M*g(x)` for some region, the ratio exceeds 1 there, that region is silently under-sampled, and the output is wrong. The bound must be verified analytically, not assumed. - **Reusing rejected proposals.** Clamping a rejected value to the boundary, or keeping it anyway when time runs out, piles mass where it does not belong. - **Capping the retry loop.** Returning the last candidate after a fixed number of failures biases the output toward whatever the proposal favours, and it does so hardest exactly where acceptance is lowest. ## The dimension problem Acceptance degrades sharply as dimension grows, because the envelope's excess volume compounds along every axis: a blanket that is 10% too generous per dimension is roughly `1.1^d` too generous overall. In high dimensions plain rejection sampling becomes unusable, and that dimensional collapse is a standard motivation for entirely different sampling machinery. ## What to say out loud Give the accept rule, state that acceptance equals `1/M` and that `M` is the expected number of proposals per draw, diagnose the loose envelope as the cause, offer a tighter proposal or the inverse-CDF route as the fix, and confirm that the accepted sample is unbiased.

  • Does a 3% acceptance rate bias the sample it produces?
    No, as long as the envelope genuinely dominates the target everywhere. Accepted draws are exactly distributed as the target; the low rate costs only time. Bias appears if the bound is violated somewhere, if rejected candidates are reused or clamped to a boundary, or if a retry loop gives up and returns the last proposal.
  • How many proposals should you expect per accepted draw?
    The count is geometric with mean `M`, the envelope constant, because acceptance is `1/M` per attempt. At a 3% rate that is about 33 proposals per draw, so a target sample of 100,000 costs roughly 3.3 million candidate evaluations. That arithmetic is what turns a loose envelope into a real runtime problem.
  • Why does rejection sampling deteriorate in high dimensions?
    The envelope's excess volume compounds across dimensions. A blanket only 10% too generous per axis is roughly `1.1^d` too generous overall, so `M` grows exponentially and acceptance collapses toward zero. Below a handful of dimensions rejection is fine; well beyond that it stops being a usable method at all.
  • What is the cleanest alternative for sampling a truncated distribution?
    Invert the truncated CDF. Map a uniform onto the retained probability range with `X = F^-1(F(a) + U*(F(b) - F(a)))`, which returns an exact draw inside `[a, b]` on every attempt with no rejection at all. It needs an invertible or numerically cheap CDF, which truncated versions of standard distributions generally have.

Think of throwing pebbles uniformly at a rectangular tray and keeping only those landing on a small island inside it. If the island covers 3% of the tray, you keep 3% of the pebbles, but the kept ones are perfectly spread over the island.

saying these in an interview costs you the question

  • Says a low acceptance rate biases the accepted draws
  • Chooses a deliberately generous M to be safe
  • Returns the last candidate after a retry cap
  • Cannot state that acceptance probability equals one over M
  • Blames the random number generator rather than the envelope

context