Python: Каков предел жесткой рекурсии для Linux, Mac и Windows?
Python sys
module предоставляет функцию setrecursionlimit
, которая позволяет вам изменить максимальный предел рекурсии Python. Документы говорят:
Максимально возможный предел зависит от платформы.
Мой вопрос: каковы максимально возможные пределы для разных платформ, под CPython? Я хотел бы знать значения для Linux, Mac и Windows.
ОБНОВЛЕНИЕ: Можем ли мы избежать ответов "Вы делаете неправильно"? Я знаю, что попытка сделать очень глубокую рекурсию - это, как правило, плохая идея. Я рассмотрел плюсы и минусы в моей конкретной ситуации и решил, что я хочу это сделать.
Ответы
Ответ 1
В Windows (по крайней мере) sys.setrecursionlimit
не полная история. Жесткий предел основан на потоке, и вам нужно вызвать threading.stack_size
и создать новый поток, когда вы достигнете определенного предела. (Я думаю, 1 МБ, но не уверен). Я использовал этот подход, чтобы увеличить его до стека в 64 МБ.
import sys
import threading
threading.stack_size(67108864) # 64MB stack
sys.setrecursionlimit(2 ** 20) # something real big
# you actually hit the 64MB limit first
# going by other answers, could just use 2**32-1
# only new threads get the redefined stack size
thread = threading.Thread(target=main)
thread.start()
Я не пытался понять, какие ограничения могут быть на threading.stack_size
, но не стесняйтесь попробовать..., где вам нужно искать.
Таким образом, sys.setrecursionlimit
- это просто предел, выполняемый самим интерпретатором. threading.stack_size
позволяет вам управлять фактическим пределом, налагаемым ОС. Если вы нажмете последний предел, Python просто полностью сработает.
Ответ 2
- Для Windows: 2000
- Для Linux: 2147483647 (2 ^ 31 - 1)
- Для Mac на моем MacBook Pro предел по умолчанию: 1000
Ответ 3
Вы не должны злоупотреблять рекурсивными вызовами в CPython. У него нет оптимизации хвоста, вызовы функций используют большую память и время обработки. Эти ограничения могут не относиться к другим реализациям, это не в чертежах.
В CPython рекурсия отлично подходит для прохождения структур данных (где для каждого должно быть достаточно предела 1000), но не для алгоритмов. Если бы я должен был реализовать, скажем, графовые алгоритмы и достигнуть предела рекурсии, я бы либо реализовал свой собственный стек, либо использовал итерации, либо искал библиотеки, реализованные в C/С++/независимо, прежде чем поднимать лимит вручную.