← Все вопросы
Почему глубокая рекурсия даёт RecursionError и как переписать её в цикл?
13
Написал рекурсивную функцию (например, сумма списка или факториал), на больших n падает с RecursionError: maximum recursion depth exceeded. Понимаю, что дело в стеке. Как переделать в итеративный вариант?
3 ответа
24
✓ Принятый ответ — помог автору
Каждый рекурсивный вызов кладёт кадр на стек вызовов, а он ограничен (в CPython по умолчанию ~1000). На глубине больше лимита — RecursionError.
Два выхода:
- Переписать в цикл, явно храня состояние. Для линейной рекурсии это обычно просто:
# было
def fact(n):
if n <= 1: return 1
return n * fact(n - 1)
# стало
def fact_iter(n):
res = 1
for i in range(2, n + 1):
res *= i
return res
- Если рекурсия по-настоящему древовидная (обход графа/дерева) — заменить стек вызовов на свой явный стек (список) и обходить им.
Поднимать лимит через sys.setrecursionlimit можно, но это костыль: рискуешь уронить интерпретатор реальным переполнением стека ОС.
Степан Михайлов Хвостовую рекурсию Python сам не оптимизирует, поэтому только ручная переделка. · 14 месяцев назад
9
Замени стек вызовов на свой список: push то, что обработать, в цикле pop и обрабатывай. Глубина перестанет упираться в лимит.
-3
sys.setrecursionlimit(100000) и всё.
Михаил Попов Это лечит симптом и может уронить процесс по-настоящему. Лучше переписать в цикл. · 14 месяцев назад
Ваш ответ
Войдите, чтобы ответить на вопрос.