Skip to contents

Computes \(\log P(K_J = k \mid \alpha)\) for \(k = 0, 1, \ldots, J\).

Usage

log_pmf_K_given_alpha(J, alpha, logS)

Arguments

J

Integer; sample size (number of observations, must be >= 1).

alpha

Numeric; DP concentration parameter (must be positive scalar).

logS

Matrix; pre-computed log-Stirling matrix from compute_log_stirling.

Value

Numeric vector of length \(J+1\) containing \(\log P(K_J = k \mid \alpha)\) for \(k = 0, 1, \ldots, J\). Entry [1] corresponds to \(k=0\) and always equals -Inf. The mathematical support is \(\{1,\ldots,J\}\); the leading structural zero is retained in the vector representation for compatibility.

Details

Uses the Antoniak distribution formula in log-space: $$\log P(K_J = k \mid \alpha) = \log|s(J,k)| + k\log\alpha - \log(\alpha)_J$$

where \(|s(J,k)|\) is the unsigned Stirling number of the first kind and \((\alpha)_J\) is the rising factorial. The implementation normalizes the equivalent log-weights over \(k=1,\ldots,J\) with log-sum-exp. This avoids cancellation in a separately evaluated log-gamma normalizer at very large finite \(\alpha\).

This log-space computation is numerically stable for large \(J\) where direct computation would overflow.

Examples

logS <- compute_log_stirling(50)
log_pmf <- log_pmf_K_given_alpha(50, 2.0, logS)

# Convert to probabilities (numerically stable softmax)
pmf <- exp(log_pmf - max(log_pmf))
pmf <- pmf / sum(pmf)
sum(pmf)  # Should be 1
#> [1] 1

# Or use pmf_K_given_alpha() directly
pmf2 <- pmf_K_given_alpha(50, 2.0, logS)
sum(pmf2)  # Should be 1
#> [1] 1