TheAlgorithms/Python · error · ValueError

factorial() not defined for negative values

Error message

factorial() not defined for negative values

What it means

Raised by factorial() in maths/factorial.py when number is integral but negative. Factorial is defined only for non-negative integers (the empty product for 0 gives 1); range(1, number + 1) with a negative number would silently return 1, so the function rejects negatives with ValueError instead.

Source

Thrown at maths/factorial.py:31

    >>> factorial(0.1)
    Traceback (most recent call last):
        ...
    ValueError: factorial() only accepts integral values
    >>> factorial(-1)
    Traceback (most recent call last):
        ...
    ValueError: factorial() not defined for negative values
    >>> factorial(1)
    1
    >>> factorial(6)
    720
    >>> factorial(0)
    1
    """
    if number != int(number):
        raise ValueError("factorial() only accepts integral values")
    if number < 0:
        raise ValueError("factorial() not defined for negative values")
    value = 1
    for i in range(1, number + 1):
        value *= i
    return value


def factorial_recursive(n: int) -> int:
    """
    Calculate the factorial of a positive integer
    https://en.wikipedia.org/wiki/Factorial

    >>> import math
    >>> all(factorial_recursive(i) == math.factorial(i) for i in range(20))
    True
    >>> factorial_recursive(0.1)
    Traceback (most recent call last):
        ...
    ValueError: factorial_recursive() only accepts integral values

View on GitHub (pinned to f5988cc097)

Solutions

  1. Validate number >= 0 at the call site with a domain-specific message.
  2. Fix the argument order or arithmetic producing the negative value (common with n - k style expressions).
  3. If negative-argument factorials are genuinely needed, use math.gamma(n + 1) and handle its poles.

Example fix

# before
factorial(n - k)  # ValueError when k > n

# after
if n < k:
    raise ValueError('need n >= k')
factorial(n - k)
Defensive patterns

Strategy: validation

Validate before calling

if number < 0:
    raise ValueError(f'factorial undefined for negative {number}')

Try / catch

try:
    r = factorial(number)
except ValueError as e:
    if 'negative values' in str(e):
        raise ValueError(f'swapped n/k or bad arithmetic produced {number}') from e
    raise

Prevention

When it happens

Trigger: Calling factorial(-1) or any negative whole value, including whole floats like -3.0 which pass the earlier integrality check. The guard is number < 0.

Common situations: Negative results of subtractions (k - n with arguments swapped); inverted loop bounds; user input with a minus sign; off-by-one errors at 0 boundaries.

Related errors


AI-assisted analysis of TheAlgorithms/Python@f5988cc097 (2026-08-14). Data as JSON: /api/errors/753c830d82e4b2b9. Report an issue: GitHub.