expm1()
expm1(x) The expm1() function computes exp(x) - 1, the exponential of the input minus one. It is more accurate than exp(x) - 1 when x is very small.
Syntax
expm1(x)
Parameters
| Parameter | Type | Default | Description |
|---|---|---|---|
x | numeric | — | A numeric vector or scalar |
Examples
Basic usage
The expm1() function is the numerically stable form of exp(x) - 1 for small inputs. When x is near zero, computing exp(x) - 1 directly loses precision because exp(x) rounds to 1 and subtracting nearly equal numbers destroys significant digits through catastrophic cancellation. expm1() uses a Taylor series expansion internally to preserve accuracy even at tiny magnitudes where the naive expression would return zero.
# expm1(0) = exp(0) - 1 = 0
expm1(0)
# [1] 0
# expm1(1) = exp(1) - 1
expm1(1)
# [1] 1.718282
# For very small values, expm1 is more accurate
x <- 1e-10
exp(x) - 1
# [1] 0 # precision lost!
expm1(x)
# [1] 1e-10 # accurate
Numerical stability demonstration
The precision difference between exp(x) - 1 and expm1(x) becomes visible below roughly abs(x) < 1e-6, where the naive subtraction loses several decimal digits. The relative error comparison below quantifies this: (exp(x) - 1 - x)/x should theoretically be very close to zero, but the naive approach shows a measurable error around 5e-8 while expm1(x) matches the true value to machine precision with zero relative error.
# When x is very small, exp(x) - 1 loses precision
x <- 1e-15
exp(x) - 1
# [1] 0 # precision lost!
expm1(x)
# [1] 1e-15 # accurate
# Relative error comparison
x <- 1e-8
(exp(x) - 1 - x) / x # relative error in exp() - 1
# [1] 5.000001e-08
(expm1(x) - x) / x # relative error in expm1()
# [1] 0
Common patterns
Financial calculations
In finance, expm1() handles continuous compounding for very small interest rates where the exponential minus one appears in present value and future value formulas. When daily or intraday rates are tiny, computing exp(rate) - 1 loses precision that can accumulate across many compounding periods. Using expm1(rate) directly preserves the full numerical accuracy needed for accurate portfolio valuation and risk calculations over extended holding periods.
# Continuous compounding returns
rate <- 0.0001
principal <- 1000
principal * expm1(rate)
# [1] 0.100005 # accurate for small rates
Probability calculations
Probability modelling depends on expm1() for accuracy in settings involving rare events. In Poisson processes and survival analysis, -expm1(-lambda) calculates the probability of at least one event occurring when the rate parameter lambda is very small. The naive computation 1 - exp(-lambda) would round to zero for tiny lambdas, incorrectly suggesting zero probability, while -expm1(-lambda) returns the correct small positive value with full floating-point precision.
# Poisson distribution: P(X = n) = exp(-lambda) * lambda^n / n!
lambda <- 1e-8
1 - exp(-lambda) # P(X > 0)
# [1] 0 # precision lost
expm1(-lambda) # -expm1(-lambda) = P(X > 0)
# [1] -1e-08 # accurate
Why expm1() exists
expm1(x) computes exp(x) - 1 with better numerical precision than evaluating exp(x) - 1 directly. When x is very small (say, 1e-10), exp(x) is very close to 1. Subtracting 1 from a number very close to 1 causes catastrophic cancellation — the result has far fewer significant digits than the inputs. expm1() avoids this by computing the result using a Taylor series that does not require subtracting nearly equal numbers.
The function matters in financial computing (compound interest for small rates), probability (Poisson log-probabilities), and any model involving small exponential increments. In Poisson regression, exp(eta) - 1 appears in mean function derivatives; using expm1(eta) directly is both faster and more accurate.
The inverse of expm1() is log1p(): log1p(expm1(x)) == x (within floating-point precision) for any finite x.
expm1() is most important when working with probabilities or rates close to zero. In R, it is used internally by several statistical functions to maintain precision. If you are implementing a custom distribution, survival model, or financial formula involving e^x - 1 for small x, always prefer expm1(x) over exp(x) - 1. The precision difference becomes visible below x ≈ 1e-6.
Beyond numerical precision, expm1() is useful as a convenient identity: expm1(0) returns exactly 0, which exp(0) - 1 also does, but the explicit intent is clearer. In simulation code, expm1(rate * time) models the probability of at least one event occurring in a Poisson process during a time period, where rate and time may be very small numbers close to zero, making numerical precision critically important for correct final results, especially in iterative statistical algorithms that accumulate small exponential increments.
Numerically, expm1(x) equals exp(x) - 1 but is computed differently to preserve accuracy. The threshold below which expm1() matters is roughly abs(x) < 0.001, where direct subtraction would lose several digits of precision.
expm1(x) computes exp(x) - 1 with higher precision than the naive expression when x is close to zero. For small x, exp(x) - 1 loses significant digits due to catastrophic cancellation; expm1() avoids this. Its complement is log1p(x), which computes log(1 + x) accurately near zero.