FermatPrimalityTest (Fermat primality test v1.0.0)

A probabilistic primality test implementation based on Fermat's Little Theorem.

Overview

This module implements the Fermat primality test, a probabilistic algorithm for determining whether a given number is likely to be prime. The test is based on Fermat's Little Theorem, which states that if $p$ is a prime number and $a$ is any integer not divisible by $p$, then:

$$ a^{p-1} \equiv 1 \pmod{p} $$

Algorithm

For a given number $n$:

  1. If $n = 1$, return false (1 is not prime)
  2. If $n = 2$, return true (2 is prime)
  3. For numbers $n > 2$:
    • Generate 100 random bases $a$ where $1 < a < n$
    • For each base, check if $\gcd(a, n) = 1$ (coprime)
    • If coprime, compute $a^{n-1} \bmod n$
    • If the result is not 1, $n$ is definitely composite
    • If all 100 tests pass, $n$ is probably prime

Mathematical Foundation

The test relies on the contrapositive of Fermat's Little Theorem: if there exists an $a$ coprime to $n$ such that $a^{n-1} \not\equiv 1 \pmod{n}$, then $n$ is composite.

However, the converse is not always true. There exist composite numbers called Fermat pseudoprimes that pass the test for some bases. Carmichael numbers are composite numbers that pass the test for all bases coprime to them.

Accuracy

  • True positives: All prime numbers will pass the test
  • False positives: Some composite numbers (pseudoprimes) may pass the test
  • False negatives: None (if the test says composite, it's definitely composite)

The probability of a false positive decreases with the number of bases tested. With 100 random bases, the probability of a false positive is extremely low for most practical purposes.

Performance

The algorithm uses efficient modular exponentiation with $O(\log n)$ complexity for each base test. The overall complexity is $O(k \log n)$ where $k$ is the number of bases tested (100 in this implementation).

Examples

iex> FermatPrimalityTest.of(2)
true

iex> FermatPrimalityTest.of(3)
true

iex> FermatPrimalityTest.of(4)
false

iex> FermatPrimalityTest.of(17)
true

iex> FermatPrimalityTest.of(100)
false

Limitations

  • This is a probabilistic test, not deterministic
  • Very large numbers may have higher false positive rates
  • For cryptographic applications, consider using deterministic tests like AKS
  • The test may be slow for very large numbers due to modular exponentiation

References

  • Fermat's Little Theorem
  • Modular Exponentiation
  • Probabilistic Primality Testing

Summary

Functions

Calculates modular exponentiation using the square-and-multiply algorithm.

Tests whether a number is prime using the Fermat primality test.

Functions

mod_pow(base, exp, mod)

Calculates modular exponentiation using the square-and-multiply algorithm.

This function efficiently computes $base^{exp} \bmod mod$ using the binary exponentiation method, also known as the square-and-multiply algorithm.

Mathematical Background

The algorithm works by expressing the exponent in binary and using the identity: $a^{2k} = (a^k)^2$ and $a^{2k+1} = a \cdot (a^k)^2$

This reduces the number of multiplications from $O(exp)$ to $O(\log exp)$.

Parameters

  • base - The base number
  • exp - The exponent (must be non-negative)
  • mod - The modulus

Returns

The result of $base^{exp} \bmod mod$

Examples

iex> FermatPrimalityTest.mod_pow(10, 2, 3)
1

iex> FermatPrimalityTest.mod_pow(7, 3, 5)
3

iex> FermatPrimalityTest.mod_pow(2, 10, 1000)
24

iex> FermatPrimalityTest.mod_pow(5, 0, 7)
1

Algorithm

  1. If $exp = 0$, return 1
  2. If $exp < 0$, raise ArithmeticError
  3. Use square-and-multiply algorithm:
    • Initialize result = 1
    • For each bit in the binary representation of exp:
      • Square the current result: $result = result^2 \bmod mod$
      • If the bit is 1, multiply by base: $result = result \cdot base \bmod mod$

Time Complexity

$O(\log exp)$ - logarithmic in the exponent.

Space Complexity

$O(1)$ - constant space usage.

Raises

of(n)

@spec of(pos_integer()) :: boolean()

Tests whether a number is prime using the Fermat primality test.

This function implements a probabilistic primality test based on Fermat's Little Theorem. It tests the number against 100 random bases to determine primality.

Parameters

  • n - The integer to test for primality

Returns

  • true if the number is probably prime
  • false if the number is definitely composite

Examples

iex> FermatPrimalityTest.of(1)
false

iex> FermatPrimalityTest.of(2)
true

iex> FermatPrimalityTest.of(3)
true

iex> FermatPrimalityTest.of(4)
false

iex> FermatPrimalityTest.of(17)
true

iex> FermatPrimalityTest.of(100)
false

Algorithm Details

  1. Edge cases: 1 returns false, 2 returns true
  2. Random base generation: Creates 100 random bases $a$ where $1 < a < n$
  3. Coprimality check: Ensures $\gcd(a, n) = 1$ using Lehmer's GCD algorithm
  4. Fermat test: Computes $a^{n-1} \bmod n$ using efficient modular exponentiation
  5. Decision: If any test fails, returns false; if all pass, returns true

Time Complexity

$O(k \log n)$ where $k = 100$ (number of bases) and $n$ is the input number.

Space Complexity

$O(1)$ - constant space usage regardless of input size.