Seite 1 von 1
recursionlimit verwenden
Verfasst: Donnerstag 1. November 2018, 11:42
von nuhakan
Hallo,
ich wollte recursionlimit verwenden. Ich weiß nicht, ob es Sinn macht oder ob überhaupt recursionlimit hier korrekt ist. Der Code soll 3 Tippfehler akzeptieren und dann zu else springen und etwas tun.
Code: Alles auswählen
def start():
# sys.setrecursionlitmi(3)
choice = input("> ")
if choice == "1":
print("1")
elif choice == "2":
print("2")
elif choice == "3":
print("3")
else:
print("1 2 3")
# Tut etwas
start()
Danke!!
Re: recursionlimit verwenden
Verfasst: Donnerstag 1. November 2018, 11:54
von noisefloor
Hallo,
nee, das macht keinen Sinn - zumal du keine Rekursion verwendest im gezeigten Code.
Deine Problemstellung löst man über `while` und einen Zähler, der feststellt, wie oft die Schleife durchlaufen wurde.
Das Rekursionslimit auf einen so niedrigen Wert wie 3 zu setzen ist auch fragwürdig, weil wenn du irgendwo in der Instanz des laufenden Python-Interpreters ein Modul hast, was Rekursion benutzt, bist du direkt an der MaxRecursionDepth und das Prog / Modul beendet sich. Weil drei Rekursonsschritte quasi nichts ist.
Python besitzt - im Gegensatz zu anderen Sprachen - auch null Optimierung für Rekursion, weswegen Rekursion bei Python fast nie verwendet wird. Iteration ist der bessere Weg, da ist Python auch viel stärker.
Gruß, noisefloor
Re: recursionlimit verwenden
Verfasst: Donnerstag 1. November 2018, 11:58
von __blackjack__
@nuhakan: Das macht keinen Sinn. Du möchtest eine ``for``-Schleife mit einem ``break`` und einem ``else``-Zweig.
@noisefloor: Deine Beschreibung klingt so als würde das Rekursionslimit tatsächlich nur bei rekursiven Aufrufen greifen: Das sind die maximal verschachtelbaren Aufrufe, egal ob nun rekursiv oder nicht. Da ist 3 also wirklich unbenutzbar und nicht nur fragwürdig.

Re: recursionlimit verwenden
Verfasst: Donnerstag 1. November 2018, 12:10
von Sirius3
Python ist sogar so schlau, das gar nicht zuzulassen:
Code: Alles auswählen
>>> import sys
>>> def start():
... sys.setrecursionlimit(3)
...
>>> start()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 2, in start
RecursionError: cannot set the recursion limit to 3 at the recursion depth 2: the limit is too low
@nuhakan: Da Du gar nicht weißt, wie tief verschachtelt Deine Funktion aufgerufen wird, kannst Du gar kein passendes Rekursionslimit setzen.
Re: recursionlimit verwenden
Verfasst: Donnerstag 1. November 2018, 12:25
von __deets__
nuhakan hat geschrieben: Donnerstag 1. November 2018, 11:42
ich wollte recursionlimit verwenden. Ich weiß nicht, ob es Sinn macht oder ob überhaupt recursionlimit hier korrekt ist. Der Code soll 3 Tippfehler akzeptieren und dann zu else springen und etwas tun.
Das ist alleine schon deshalb nicht richtig, weil du eine globale Einstellung des Interpreters lokal zur Flusskontrolle ausnutzt. Selbst wenn dein Code funktionieren wuerde, handelst du dir damit massiv Probleme ein. Starte mal einen Thread im Hintegrund, der dann ploetzlich stirbt, weil er das Limit ueberschreitet. Oder das einfuegen eines Bibliotheksaufrufs, dessen tiefe du gar nicht kennst, oder die sich in einer anderen Pythonversion anders gestaltet, und die Nummer kracht.
Re: recursionlimit verwenden
Verfasst: Donnerstag 1. November 2018, 12:40
von __blackjack__
@Sirius3: Naja, man könnte das ja mit ``len(inspect.stack())`` ermitteln und drei drauf addieren. Das Problem ist eher in der anderen Richtung, nicht das man nicht weiss auf welcher Ebene man bereits steht, sondern wie viele Ebenen benutzte Funktionen wie `input()` und `print()` da vielleicht noch tiefer gehen wollen/müssen.
@__deets__: Threads müssten da doch eigentlich ihre eigenen Stacks haben‽
Re: recursionlimit verwenden
Verfasst: Donnerstag 1. November 2018, 12:51
von __deets__
@__blackjack__: aber setrecursionlimit ist global.
Code: Alles auswählen
Traceback (most recent call last):
File "/tmp/test.py", line 15, in <module>
t = threading.Thread(target=test)
File "/usr/lib/python3.6/threading.py", line 793, in __init__
self._started = Event()
File "/usr/lib/python3.6/threading.py", line 499, in __init__
self._cond = Condition(Lock())
RecursionError: maximum recursion depth exceeded while calling a Python object
Error in sys.excepthook:
Traceback (most recent call last):
File "/usr/lib/python3/dist-packages/apport_python_hook.py", line 53, in apport_excepthook
if not enabled():
File "/usr/lib/python3/dist-packages/apport_python_hook.py", line 28, in enabled
return re.search(r'^\s*enabled\s*=\s*0\s*$', conf, re.M) is None
File "/usr/lib/python3.6/re.py", line 182, in search
return _compile(pattern, flags).search(string)
File "/usr/lib/python3.6/re.py", line 301, in _compile
p = sre_compile.compile(pattern, flags)
File "/usr/lib/python3.6/sre_compile.py", line 562, in compile
p = sre_parse.parse(p, flags)
File "/usr/lib/python3.6/sre_parse.py", line 847, in parse
source = Tokenizer(str)
RecursionError: maximum recursion depth exceeded
Original exception was:
Traceback (most recent call last):
File "/tmp/test.py", line 15, in <module>
t = threading.Thread(target=test)
File "/usr/lib/python3.6/threading.py", line 793, in __init__
self._started = Event()
File "/usr/lib/python3.6/threading.py", line 499, in __init__
self._cond = Condition(Lock())
RecursionError: maximum recursion depth exceeded while calling a Python object
Produziert von
Code: Alles auswählen
import sys
import threading
import time
sys.setrecursionlimit(100)
def recursive(count):
if count:
recursive(count-1)
def test():
time.sleep(3)
recursive(200)
t = threading.Thread(target=test)
t.daemon = True
t.start()
while True:
recursive(8)
Re: recursionlimit verwenden
Verfasst: Donnerstag 1. November 2018, 12:55
von __deets__
Nachtrag: ich musste das Rekursionslimit hochsetzen, weil man mit nur 10 noch nicht mal den Thread hochgezogen bekommt (mein anderer Punkt). Aber bei 100 schlaegt der Thread fehl. Das hat ja nix mit dessen Stack, sondern nur der globalen Einstellung fuer desset tiefe zu tun.
Re: recursionlimit verwenden
Verfasst: Donnerstag 1. November 2018, 13:01
von nuhakan
Vielen Dank für die Antworten. Ich weiß, besser mit 'for' oder 'while'. Es war nur ein Gedanke zum Üben. Und jetzt lese ich euch, um 'recursionlimit' besser zu verstehen.
Grüße.