Ich brauche eine Funktion, die n nimmt und 2 n - 1 zurückgibt . Es klingt einfach genug, aber die Funktion muss rekursiv sein. Bisher habe ich nur 2 n :
def required_steps(n):
if n == 0:
return 1
return 2 * req_steps(n-1)
In der Übung heißt es: "Sie können davon ausgehen, dass der Parameter n immer eine positive ganze Zahl und größer als 0 ist."
1 << n
können daher nicht überlaufen. Dies scheint eine Übung zu sein, um einen Weg zu finden, sich(1<<n) - 1
in mehrere Schritte zu zerlegen , wobei möglicherweise jedes Bit einzeln gesetzt wird, wie einige Antworten zeigen.def fn(n): if n == 0: return 1; return (2 << n) - fn(0); # technically recursive
C:\MyFolder
Antworten:
2**n -1
ist auch 1 + 2 + 4 + ... + 2 n-1, was zu einer einzigen rekursiven Funktion gemacht werden kann (ohne dass die zweite 1 von der Potenz von 2 subtrahiert).Hinweis : 1 + 2 * (1 + 2 * (...))
Lösung unten, schauen Sie nicht, ob Sie den Hinweis zuerst versuchen möchten.
Dies funktioniert, wenn
n
garantiert größer als Null ist (wie in der Problemstellung tatsächlich versprochen):Eine robustere Version würde auch Null- und negative Werte verarbeiten:
(Das Hinzufügen eines Schecks für Nicht-Ganzzahlen bleibt als Übung übrig.)
quelle
required_steps(0)
jetzt verursacht unendliche Rekursion2^0 - 1
== 0. Fügen Sieif
für diesen Fall eine weitere hinzu.int
, wissen wir nicht, was wir tun sollen, wenn n <0 ist. Berechnung? Einen Fehler werfen? 0 zurückgeben? In diesem Fall können wir nur eine Teilfunktion ausführen (definieren Sie sie für Dinge, von denen wir wissen, was das Ergebnis ist).0
und wirdn - 1
für das Teilproblem verwendet. Eine Domäne natürlicher Zahlen scheint gut zu passen.Um ein Problem mit einem rekursiven Ansatz zu lösen, müssten Sie herausfinden, wie Sie die Funktion mit einer bestimmten Eingabe in Bezug auf dieselbe Funktion mit einer anderen Eingabe definieren können. In diesem Fall können Sie seitdem
f(n) = 2 * f(n - 1) + 1
:damit:
Ausgänge:
quelle
Sie können den wirklich rekursiven Teil in eine andere Funktion extrahieren
Oder Sie können ein Flag setzen und festlegen, wann subtrahiert werden soll
quelle
Verwenden eines zusätzlichen Parameters für das Ergebnis,
r
-Sie können es auch mit bitweiser Linksverschiebung schreiben,
<<
-Die Ausgabe ist die gleiche
quelle
else
Klausel in beiden Funktionenr * 2
zur << 1
und das ist "überhaupt nicht lesbar"? 😂n
mal und dann subtrahiert 1. Scheint noch weniger elegant dann notwendig, obwohl das Ganze eine Übung in der Ineffizienz vs. ist(1<<n) - 1
.Haben Sie einen Platzhalter, um sich den ursprünglichen Wert von n zu merken
n == N
, und kehren Sie dann für den allerersten Schritt zurück2^n-1
quelle
Eine Möglichkeit, den Offset von "-1" zu erhalten, besteht darin, ihn in der Rückgabe des ersten Funktionsaufrufs mit einem Argument mit einem Standardwert anzuwenden und das Offset-Argument während der rekursiven Aufrufe explizit auf Null zu setzen.
quelle
Zusätzlich zu den fantastischen Antworten, die zuvor gegeben wurden, wird unten die Implementierung mit inneren Funktionen gezeigt.
Grundsätzlich weist es k einen globalen Wert von n zu und rekursiert ihn mit geeigneten Vergleichen durch.
quelle