In the previous lesson, we introduced random variables and described their probability distributions through probability mass functions, probability density functions, and distribution functions.
In this lesson, we begin a gallery of probability distributions that occur frequently in applications. We first consider discrete random variables. The main examples are the Bernoulli, binomial, geometric, and Poisson distributions.
The expectation and variance of these distributions will be studied systematically in a later lesson. Here we concentrate on understanding how the distributions arise and what their parameters mean.
Bernoulli random variables¶
A Bernoulli experiment is an experiment with two possible outcomes, conventionally called success and failure.
Let denote the event corresponding to a success. We write
and therefore the probability of failure is
We assume throughout that
A Bernoulli random variable is defined by assigning the value 1 to a success and the value 0 to a failure:
Thus, its probability mass function is
We say that has a Bernoulli distribution with parameter , and write
The Bernoulli distribution is the simplest nontrivial discrete probability distribution. It is used whenever an observation can be classified into two possible categories.
For example, a manufactured component may be classified as defective or non-defective, a transmitted bit may be received correctly or incorrectly, or a medical test may produce a positive or negative result.
Repeated Bernoulli trials and the binomial distribution¶
Suppose that the same Bernoulli experiment is repeated times.
We assume that
the trials are independent;
the probability of success is the same, namely , in every trial.
Let denote the outcome of the th trial:
The number of successes in the trials is therefore the random variable
The event consists of all sequences of trials containing exactly successes and failures.
Consider one particular sequence containing successes and failures. By independence, its probability is
The number of sequences containing exactly successes is
Consequently,
This is the binomial distribution. We write
The two parameters have a direct interpretation:
is the number of trials;
is the probability of success in each trial.
The binomial distribution therefore models the number of successes obtained in a fixed number of independent and identically distributed Bernoulli trials.
import matplotlib.pyplot as plt
import numpy as np
from scipy.stats import binom
# 1. Define distribution parameters
n = 20 # Total number of trials
p = 0.4 # Probability of success on each trial
# 2. Generate integer k values (from 0 up to n successes)
k = np.arange(0, n + 1)
# 3. Compute PMF and CDF values
pmf_values = binom.pmf(k, n=n, p=p)
cdf_values = binom.cdf(k, n=n, p=p)
# 4. Create side-by-side plots
fig, (ax1, ax2) = plt.subplots(1, 2, figsize=(12, 5))
# Plot 1: Probability Mass Function P(X = k)
ax1.vlines(k, 0, pmf_values, colors='navy', lw=2)
ax1.plot(
k,
pmf_values,
'o',
color='navy',
markersize=6,
label=fr'$\mathrm{{Binom}}(n={n}, p={p})$',
)
ax1.set_title(r'Probability Mass Function $P(X = k)$', fontsize=12)
ax1.set_xlabel('k (number of successes)')
ax1.set_ylabel(r'Probability $P(X = k)$')
ax1.grid(True, linestyle='--', alpha=0.6)
ax1.legend()
# Plot 2: Cumulative Distribution Function F(k)
ax2.step(k, cdf_values, where='post', color='crimson', lw=2, label=r'$F(k)$')
ax2.plot(k, cdf_values, 'o', color='crimson', alpha=0.5, markersize=4)
ax2.set_title(r'Cumulative Distribution Function $F(k)$', fontsize=12)
ax2.set_xlabel('k (number of successes)')
ax2.set_ylabel(r'Probability $F(k)$')
ax2.grid(True, linestyle='--', alpha=0.6)
ax2.legend()
plt.tight_layout()
plt.show()
The Negative Binomial Distribution¶
Consider again a sequence of independent Bernoulli trials, each with success probability and failure probability .
Instead of fixing the total number of trials in advance, suppose we continue performing trials until a target number of successes is achieved ().
Let the random variable denote the number of failures observed before achieving the th success.
The event means that:
the th trial is the th success;
among the first trials, there are exactly successes and failures.
By independence of the trials, the probability of any specific sequence of trials containing successes and failures with a success at the final trial is
The number of ways to choose the positions of the first successes among the first trials is given by the binomial coefficient
Consequently, the probability mass function of is
This is the negative binomial distribution. We write
The two parameters have a direct interpretation:
is the target number of successes;
is the probability of success in each trial.
The negative binomial distribution therefore models the number of failures encountered before obtaining a fixed number of successes in independent and identically distributed Bernoulli trials.
import matplotlib.pyplot as plt
import numpy as np
from scipy.stats import nbinom
# 1. Define distribution parameters
r = 5 # Target number of successes
p = 0.4 # Probability of success on each trial
# 2. Generate integer k values (number of failures before r successes)
k = np.arange(0, 25)
# 3. Compute PMF and CDF values
pmf_values = nbinom.pmf(k, n=r, p=p)
cdf_values = nbinom.cdf(k, n=r, p=p)
# 4. Create side-by-side plots
fig, (ax1, ax2) = plt.subplots(1, 2, figsize=(12, 5))
# Plot 1: Probability Mass Function P(X = k)
ax1.vlines(k, 0, pmf_values, colors='navy', lw=2)
ax1.plot(
k,
pmf_values,
'o',
color='navy',
markersize=6,
label=fr'$\mathrm{{NBinom}}(r={r}, p={p})$',
)
ax1.set_title(r'Probability Mass Function $P(X = k)$', fontsize=12)
ax1.set_xlabel('k (number of failures)')
ax1.set_ylabel(r'Probability $P(X = k)$')
ax1.grid(True, linestyle='--', alpha=0.6)
ax1.legend()
# Plot 2: Cumulative Distribution Function F(k)
ax2.step(k, cdf_values, where='post', color='crimson', lw=2, label=r'$F(k)$')
ax2.plot(k, cdf_values, 'o', color='crimson', alpha=0.5, markersize=4)
ax2.set_title(r'Cumulative Distribution Function $F(k)$', fontsize=12)
ax2.set_xlabel('k (number of failures)')
ax2.set_ylabel(r'Probability $F(k)$')
ax2.grid(True, linestyle='--', alpha=0.6)
ax2.legend()
plt.tight_layout()
plt.show()
The geometric distribution¶
The binomial distribution counts the number of successes in a fixed number of trials.
A different question is obtained when we continue performing independent Bernoulli trials until the first success occurs.
Let denote the number of trials required to obtain the first success.
For to take the value , the first trials must all be failures and the th trial must be a success. Therefore,
Thus, the probability mass function is
This is called the geometric distribution with parameter , and we write
The geometric distribution is therefore a waiting-time distribution: it describes how many independent Bernoulli trials are needed before the first success.
For example, if a communication system successfully transmits a packet with probability at every attempt, then the number of attempts required for the first successful transmission has a geometric distribution.
The first few probabilities are
The probabilities decrease geometrically as the waiting time increases.
The distribution is correctly normalized because
import matplotlib.pyplot as plt
import numpy as np
from scipy.stats import geom
# 1. Define distribution parameter
p = 0.3 # Probability of success on each trial
# 2. Generate integer k values starting from 1 (first success)
# Range set to cover ~99.9% of the distribution tail
k_max = int(geom.ppf(0.999, p))
k = np.arange(1, k_max + 1)
# 3. Compute PMF and CDF values
pmf_values = geom.pmf(k, p=p)
cdf_values = geom.cdf(k, p=p)
# 4. Create side-by-side plots
fig, (ax1, ax2) = plt.subplots(1, 2, figsize=(12, 5))
# Plot 1: Probability Mass Function P(X = k)
ax1.vlines(k, 0, pmf_values, colors='navy', lw=2)
ax1.plot(
k,
pmf_values,
'o',
color='navy',
markersize=6,
label=fr'$\mathrm{{Geom}}(p={p})$',
)
ax1.set_title(r'Probability Mass Function $P(X = k)$', fontsize=12)
ax1.set_xlabel('k (number of trials)')
ax1.set_ylabel(r'Probability $P(X = k)$')
ax1.grid(True, linestyle='--', alpha=0.6)
ax1.legend()
# Plot 2: Cumulative Distribution Function F(k)
ax2.step(k, cdf_values, where='post', color='crimson', lw=2, label=r'$F(k)$')
ax2.plot(k, cdf_values, 'o', color='crimson', alpha=0.5, markersize=4)
ax2.set_title(r'Cumulative Distribution Function $F(k)$', fontsize=12)
ax2.set_xlabel('k (number of trials)')
ax2.set_ylabel(r'Probability $F(k)$')
ax2.grid(True, linestyle='--', alpha=0.6)
ax2.legend()
plt.tight_layout()
plt.show()
The Poisson distribution¶
The binomial distribution describes the number of successes in a fixed number of trials.
There are situations, however, in which events are naturally described as rare occurrences over a large number of opportunities. Examples include:
defects in a large production batch;
failures of components during a fixed period of operation;
calls arriving at a service centre;
accidents occurring along a stretch of road;
radioactive decay events during a fixed time interval.
Suppose that
Thus, the number of opportunities becomes large, the probability of success at each opportunity becomes small, while the expected number of successes remains of order one.
In this regime, the binomial distribution approaches the Poisson distribution.
For fixed ,
This motivates the following definition.
The parameter represents the typical number of occurrences in the interval, region, or population being considered. The fact that the same parameter will later turn out to be both the mean and the variance will be derived when moments are studied.
import matplotlib.pyplot as plt
import numpy as np
from scipy.stats import poisson
# 1. Define distribution parameter
lam = 5 # Lambda (average rate / mean)
# 2. Generate integer x values (Poisson is non-negative and discrete)
# We cover roughly 4 standard deviations (std = sqrt(lambda))
x_max = int(lam + 4 * np.sqrt(lam)) + 1
x = np.arange(0, x_max)
# 3. Compute PMF and CDF values
pmf_values = poisson.pmf(x, mu=lam)
cdf_values = poisson.cdf(x, mu=lam)
# 4. Create side-by-side plots
fig, (ax1, ax2) = plt.subplots(1, 2, figsize=(12, 5))
# Plot 1: Probability Mass Function P(X = k)
ax1.vlines(x, 0, pmf_values, colors='navy', lw=2)
ax1.plot(
x,
pmf_values,
'o',
color='navy',
markersize=6,
label=fr'$\mathrm{{Poisson}}(\lambda={lam})$',
)
ax1.set_title(r'Probability Mass Function $P(X = k)$', fontsize=12)
ax1.set_xlabel('k')
ax1.set_ylabel(r'Probability $P(X = k)$')
ax1.grid(True, linestyle='--', alpha=0.6)
ax1.legend()
# Plot 2: Cumulative Distribution Function F(k)
ax2.step(x, cdf_values, where='post', color='crimson', lw=2, label=r'$F(k)$')
ax2.plot(x, cdf_values, 'o', color='crimson', alpha=0.5, markersize=4)
ax2.set_title(r'Cumulative Distribution Function $F(k)$', fontsize=12)
ax2.set_xlabel('k')
ax2.set_ylabel(r'Probability $F(k)$')
ax2.grid(True, linestyle='--', alpha=0.6)
ax2.legend()
plt.tight_layout()
plt.show()
Why does the Poisson formula arise?¶
The connection with the binomial distribution can be seen directly.
Suppose that . Then
For fixed ,
while
and
Combining these limits gives (7).
Thus, the Poisson distribution can be regarded as the limiting model for a large number of independent trials with a small probability of success.
The Compound Poisson Distribution¶
In many practical situations, we are interested not only in the number of events that occur, but also in the total accumulated value associated with those events. Examples include:
the total monetary amount of insurance claims filed in a year (where is the number of claims and is the claim size);
the total amount of rainfall in a region (where is the number of storms and is the rainfall per storm);
the total expenditure of customers in a store (where is the number of customers and is the amount spent by the th customer).
This naturally leads to the concept of a compound Poisson distribution.
The parameter represents the expected frequency of events, while the distribution of models the random severity or size of each individual event.
import matplotlib.pyplot as plt
import numpy as np
# 1. Define distribution parameters
a = 10 # Expected number of events N ~ Pois(a)
num_samples = 100000
# 2. Simulate N and claim sizes X_i
np.random.seed(42)
N_samples = np.random.poisson(lam=a, size=num_samples)
# Suppose each X_i is discrete with values {10, 20, 50} and probabilities [0.5, 0.3, 0.2]
x_vals = np.array([10, 20, 50])
x_probs = np.array([0.5, 0.3, 0.2])
S_samples = np.zeros(num_samples)
for i in range(num_samples):
if N_samples[i] > 0:
S_samples[i] = np.sum(np.random.choice(x_vals, size=N_samples[i], p=x_probs))
# 3. Create side-by-side plots
fig, (ax1, ax2) = plt.subplots(1, 2, figsize=(12, 5))
# Plot 1: Simulated Distribution Histogram
ax1.hist(S_samples, bins=40, density=True, color='navy', alpha=0.7, edgecolor='black')
ax1.set_title(r'Simulated Compound Poisson PMF/Density', fontsize=12)
ax1.set_xlabel('Total Sum $S$')
ax1.set_ylabel('Probability Density')
ax1.grid(True, linestyle='--', alpha=0.6)
# Plot 2: Empirical Cumulative Distribution Function
sorted_S = np.sort(S_samples)
cdf_empirical = np.arange(1, num_samples + 1) / num_samples
ax2.plot(sorted_S, cdf_empirical, color='crimson', lw=2, label=r'Empirical $F(S)$')
ax2.set_title(r'Empirical Cumulative Distribution Function $F(S)$', fontsize=12)
ax2.set_xlabel('Total Sum $S$')
ax2.set_ylabel(r'Probability $F(S)$')
ax2.grid(True, linestyle='--', alpha=0.6)
ax2.legend()
plt.tight_layout()
plt.show()
The Mixed Poisson Distribution¶
In the standard Poisson model, the rate parameter is assumed to be constant across all observations. In many engineering and real-world applications, however, environmental conditions, operational stress, or batch-to-batch material variations cause the underlying intensity parameter to fluctuate randomly from one system or time window to another.
This leads to the mixed Poisson distribution (or Poisson mixture), where the intensity parameter itself is modeled as a non-negative random variable .
The mixing distribution represents the uncertainty or population heterogeneity in the event rate across different operating environments.
import matplotlib.pyplot as plt
import numpy as np
from scipy.stats import gamma, poisson
# 1. Define mixing distribution parameters (Gamma distribution for rate Lambda)
shape = 3.0 # Gamma shape parameter r
scale = 1.5 # Gamma scale parameter theta
# 2. Generate grid of k values
k_vals = np.arange(0, 25)
# 3. Numerically evaluate unconditional PMF P(X = k)
pmf_mixed = np.zeros_like(k_vals, dtype=float)
for i, k in enumerate(k_vals):
# Integrand: Pois(k | lambda) * Gamma(lambda)
integrand = lambda lam: poisson.pmf(k, mu=lam) * gamma.pdf(lam, a=shape, scale=scale)
# Integrate over lambda in [0, inf)
from scipy.integrate import quad
pmf_mixed[i], _ = quad(integrand, 0, np.inf)
# 4. Plot Mixed Poisson PMF
plt.figure(figsize=(7, 4.5))
plt.vlines(k_vals, 0, pmf_mixed, colors='navy', lw=2)
plt.plot(k_vals, pmf_mixed, 'o', color='navy', markersize=6, label=r'Mixed Poisson ($\Lambda \sim \mathrm{Gamma}$)')
plt.title(r'Probability Mass Function of Mixed Poisson Distribution', fontsize=12)
plt.xlabel('k (number of events)')
plt.ylabel(r'Probability $P(\xi = k)$')
plt.grid(True, linestyle='--', alpha=0.6)
plt.legend()
plt.tight_layout()
plt.show()
Comparing the discrete distributions¶
The distributions introduced in this lesson describe different types of counting problems.
| Distribution | Random quantity | Parameters | Typical question |
|---|---|---|---|
| Bernoulli | One success/failure outcome | Does the event occur? | |
| Binomial | Number of successes in trials | How many successes occur? | |
| Geometric | Number of trials before first success | How long until the first success? | |
| Negative Binomial | Number of failures before successes | How many failures occur before a given number of successes? | |
| Poisson | Number of rare events | How many events occur in a given interval? |
The relationships between these distributions are particularly important.
A Bernoulli random variable represents a single trial. The binomial distribution counts successes in a fixed number of independent Bernoulli trials. The geometric distribution instead counts how many trials are needed to obtain the first success, while the negative binomial distribution generalizes this to count failures before achieving a target number of successes. Finally, the Poisson distribution arises as a limiting model for rare successes when the number of opportunities is large.
These distinctions are often more important in applications than the formulas themselves: choosing a probability distribution means identifying the random mechanism that generates the observations.
A short computational illustration¶
The binomial and Poisson distributions can be compared when is large and is small.
For example, consider
so that
The corresponding binomial distribution is therefore expected to be close to a Poisson distribution with parameter .
import numpy as np
import matplotlib.pyplot as plt
from scipy.stats import binom, poisson
n = 1000
p = 0.002
a = n * p
k = np.arange(0, 12)
binomial_pmf = binom.pmf(k, n, p)
poisson_pmf = poisson.pmf(k, a)
plt.figure(figsize=(8, 5))
plt.plot(
k,
binomial_pmf,
"o-",
label=r"$\operatorname{Bin}(1000,0.002)$"
)
plt.plot(
k,
poisson_pmf,
"s--",
label=r"$\operatorname{Pois}(2)$"
)
plt.xlabel("Number of successes")
plt.ylabel("Probability")
plt.title("Binomial distribution and Poisson approximation")
plt.grid(True, alpha=0.3)
plt.legend()
plt.show()
The two distributions are very close in this example. This illustrates why the Poisson distribution is useful: it can replace a binomial model when is large and is small, while keeping the average number of successes fixed.
Summary¶
The main discrete probability distributions introduced in this lesson are:
Bernoulli: one trial with two possible outcomes; Binomial: the number of successes in a fixed number of independent Bernoulli trials; Geometric: the number of trials required to obtain the first success; Poisson: the number of rare events occurring in a specified setting.
The binomial and Poisson distributions are connected by the rare-event limit
In the next lesson we turn to important continuous probability distributions, in particular the uniform, exponential, and normal distributions. We will also see how the normal distribution emerges as a limit of the binomial distribution, providing the first step toward the central limit theorem.