fuckingpython.lol

Python errors › RecursionError

RecursionError: maximum recursion depth exceeded

Updated

The Python error "maximum recursion depth exceeded" means a function called itself about 1,000 times without stopping. Usually a missing base case. How to find it.

What you see

main.py
def factorial(n):
    return n * factorial(n - 1)

print(factorial(5))
Python 3.15 prints
Traceback (most recent call last):
  File "/home/me/project/main.py", line 4, in <module>
    print(factorial(5))
          ~~~~~~~~~^^^
  File "/home/me/project/main.py", line 2, in factorial
    return n * factorial(n - 1)
               ~~~~~~~~~^^^^^^^
  File "/home/me/project/main.py", line 2, in factorial
    return n * factorial(n - 1)
               ~~~~~~~~~^^^^^^^
  File "/home/me/project/main.py", line 2, in factorial
    return n * factorial(n - 1)
               ~~~~~~~~~^^^^^^^
  [Previous line repeated 996 more times]
RecursionError: maximum recursion depth exceeded

What it means

Every call adds a frame to the call stack. Python limits how deep that stack may get, 1,000 frames by default, so that runaway recursion stops with an exception instead of crashing the interpreter. factorial never stops calling itself, so it hits the limit.

The traceback repeats the same lines and then says how many times they repeated, so the function that loops is the one named in those lines.

Why it happens

  • No base case, as in the example: nothing returns without calling again.
  • A base case that is never reached, such as if n == 0 when n starts negative or steps by 2.
  • A property or __getattr__ that calls itself. Reading self.name inside the name property, or setting self.x inside __setattr__, recurses on every access.
  • Two functions that call each other with no exit.
  • Recursion over deep data, such as a linked list or tree thousands of levels deep, where the code is correct but the depth is real.

How to fix it

Give the function a case that returns without recursing:

def factorial(n):
    if n <= 1:
        return 1
    return n * factorial(n - 1)

For a property, store the value under another name:

class User:
    @property
    def name(self):
        return self._name

For deep data that is genuinely deep, rewrite the recursion as a loop with your own stack. Raising the limit with sys.setrecursionlimit() works for moderate depths, but too high a limit can crash the interpreter instead of raising.

How each Python version words it

PythonPrints
3.9–3.15RecursionError: maximum recursion depth exceeded

Run on CPython 3.9.6, 3.10.22, 3.11.17, 3.12.15, 3.13.17, 3.14.9 and 3.15.1, on October 25, 2026.

The wording is the same in every version here. What changed in 3.12 is what the limit counts: it now applies only to Python code, and builtin functions are protected from runaway recursion by a separate mechanism.

Questions

What is the default limit?

1,000, as sys.getrecursionlimit() reports. The real depth of your code is a little less, because the interpreter's own frames count too.

Does Python optimise tail calls?

No. A function that returns a call to itself still adds a frame for every call, so a loop is the way to go deep.

Sources

Read on October 25, 2026.