How to Use math.comb and math.perm in Python
Python provides built-in tools for combinatorial calculations through
the math.comb() and math.perm() functions
introduced in Python 3.8. This article explains how these functions
calculate combinations and permutations, their syntax and mathematical
formulas, their handling of edge cases, and the underlying performance
optimizations that make them superior to manual implementations using
factorials.
Permutations with
math.perm()
A permutation represents the number of ways to choose and arrange \(k\) items from a set of \(n\) distinct items where the order of selection matters.
The mathematical formula for a permutation is:
\[P(n, k) = \frac{n!}{(n - k)!}\]
In Python, the syntax is:
import math
math.perm(n, k=None)The function takes two arguments:
n: A non-negative integer representing the total number of items.k(optional): A non-negative integer representing the number of items to arrange. If \(k\) is not specified or set toNone, the function defaults to \(k = n\), calculating \(n!\) (the full factorial of \(n\)).
Example Usage
import math
# Number of ways to award 1st, 2nd, and 3rd place among 10 competitors
podium_finishes = math.perm(10, 3)
print(podium_finishes) # Output: 720
# Full arrangement of 5 items (equivalent to math.factorial(5))
all_arrangements = math.perm(5)
print(all_arrangements) # Output: 120If \(k > n\),
math.perm(n, k) returns 0 because it is
impossible to choose more items than are available. If either \(n\) or \(k\) is negative or not an integer, a
ValueError or TypeError is raised.
Combinations with
math.comb()
A combination represents the number of ways to choose \(k\) items from a set of \(n\) items where the order of selection does not matter.
The mathematical formula for a combination is:
\[C(n, k) = \binom{n}{k} = \frac{n!}{k!(n - k)!}\]
In Python, the syntax is:
import math
math.comb(n, k)Both arguments \(n\) and \(k\) are required and must be non-negative integers.
Example Usage
import math
# Number of ways to choose a 4-person committee from a group of 12
committee = math.comb(12, 4)
print(committee) # Output: 495
# Choosing 0 items from 10 always yields 1 way
empty_set = math.comb(10, 0)
print(empty_set) # Output: 1Similar to math.perm(), if \(k
> n\), math.comb(n, k) evaluates to
0. Passing negative values or non-integers raises a
ValueError or TypeError.
How They Compute Combinatorics Internally
Naively implementing permutations or combinations using
math.factorial() is computationally inefficient. Computing
full factorials such as \(n!\) produces
extremely large intermediate numbers, consuming significant memory and
processor time before division cancels out the common terms.
Instead, Python’s C implementation uses optimized arithmetic algorithms:
Direct Multiplicative Cancellation: For permutations,
math.perm(n, k)computes only the falling factorial:\[n \times (n - 1) \times \dots \times (n - k + 1)\]
This performs exactly \(k\) multiplications instead of computing the full \(n!\) and \((n - k)!\).
Symmetry Optimization: For combinations, \(\binom{n}{k}\) is mathematically identical to \(\binom{n}{n - k}\). If \(k > n / 2\),
math.comb()automatically sets \(k = n - k\). This minimizes the number of multiplication and division steps.C-Level Big Integer Handling: Both functions are implemented directly in C within CPython. They use intermediate reductions to keep number sizes manageable throughout evaluation, returning an exact Python integer regardless of magnitude without risk of floating-point overflow.