Ich bin an einem Problem arbeiten, die eine rekursive Funktion und haben festgestellt, erfordert, dass verschachtelte Ausführungen der Eltern Parameter modifizieren zu sein scheinen:Haben rekursive Funktionen spezielle Scoping-Regeln?
var foo = function(ar) {
console.log('Calling function - Array: ' + ar.toString());
if(ar.length > 1){
var ele = ar.pop();
foo(ar);
console.log('Function recursion ends - Array: ' + ar.toString() + ' Popped: ' + ele);
return;
} else {
console.log('Function ends - Array: ' + ar.toString());
return;
}
}
foo([1,2,3]);
Ausgänge (Einzug von mir):
/* Calling function - Array: 1,2,3 Calling function - Array: 1,2 Calling function - Array: 1 Function ends - Array: 1 Function recursion ends - Array: 1 Popped: 2 Function recursion ends - Array: 1 Popped: 3 <-- What happened to 2? */
Das scheint seltsam - weil ich die Funktion mit [1,2,3]
aufgerufen habe und ich würde erwarten, dass die erste Iteration der Funktion alle Elemente beibehalten, die zwischenbereitgestellt werdenund ele
- aber stattdessen, wenn die Funktion endet, bleibt nur 1
im bereitgestellten Array - was ist mit 2
passiert? Hat die verschachtelte Ausführung pop
es aus der Variablen der ersten Ausführung?
Mein Verständnis von Funktionsumfang in JavaScript würde sagen, dass an eine Funktion übergeben Variablen nur lokal ändern können und sie nicht zurück zu den global/Eltern Umfang exportieren wie hier zu sehen:
var bar = 'bar';
function doBar(bar){
bar = 'foo';
}
doBar(bar);
console.log(bar); //Outputs 'bar';
Aber der Ausgang von der rekursiven Funktion scheint dieses Verständnis herauszufordern.
Wie kann ich verhindern, dass diese verschachtelten Ausführungen den Parent-Parameter ändern, um die fehlende 2
zurück zu bringen? Ist mein Verständnis von Scoping in JavaScript falsch?
In meinem erbärmlichen Versuch an Strohhalme zu erfassen, bevor diese Frage zu öffnen, habe ich versucht, die Funktion innerhalb einer Schließung Ausführung:
var foo = function(ar) {
console.log('Calling function - Array: ' + ar.toString());
if(ar.length > 1){
var ele = ar.pop();
(function(foo, ar){
foo(ar);
})(foo, ar)
console.log('Function recursion ends - Array: ' + ar.toString() + ' Popped: ' + ele);
return;
} else {
console.log('Function ends - Array: ' + ar.toString());
return;
}
}
Aber ich habe die gleichen Ergebnisse wie ohne den Verschluss mit - Ich vermute, weil ich explizit in ar
und foo
übergeben habe es nicht anders als ohne die Schließung.
Nested foo() auf Array ausgeführt, bevor Sie etwas anmelden. Versuchen Sie, vor dem verschachtelten 'foo()' zu loggen. – charlietfl
Nein, die Rekursion hat nichts besonderes zu tun, und das hat nichts mit Scope zu tun. Jeder Aufruf erzeugt eine eigene 'ar'-Variable. Sie verweisen nur auf das gleiche Array-Objekt und "pop" mutiert es. – Bergi
Nach dieser Zeit beginnen Sie zu loggen 'Funktion Rekursion endet ...' Was ist "ist" gegeben, was die Konsole Ihnen sagt? – JonSG