2016-08-01 8 views
2

Wenn ich die Funktion once wieJS rekursiven Funktionsaufruf

dies nennen
var button = document.querySelector('button'); 

button.addEventListener('click', once); 

function once() { 
    console.log('one'); 

    button.removeEventListener('click', once); 
} 

Es ist nur einmal aufgerufen wird.

Aber wenn ich genannt wie dieses once()

var button = document.querySelector('button'); 

button.addEventListener('click', once()); 

function once() { 
    console.log('one'); 

    button.removeEventListener('click', once()); 
} 

Exception wirft

Exception: InternalError: too much recursion

Könnten Sie bitte erklären, warum dies geschieht.

+0

Sie rufen sofort eine Funktion mit '()' darin auf –

+1

Wenn Sie das '()' nach dem Funktionsnamen verwenden, wird die Funktion ausgeführt. Und Sie möchten nicht ausgeführt werden, wenn Sie Methoden wie 'addEventListener' oder' removeEventListener' übergeben, also entfernen Sie sie einfach. –

+2

Haha ich liebe die Ausnahme, die es wirft - "zu viel Rekursion" –

Antwort

2

() nach Funktionsname aufrufen ist die Funktion. Als button.addEventListener('click', once()); binden Sie den Rückgabewert once() Methode, die undefiniert ist.

Und da once() rekursiv ohne jede break-Anweisung aufgerufen wird, erhalten Sie die InternalError: too much recursion.

Sie sollten die Funktionsreferenz übergeben.

button.addEventListener('click', once); 

Für Zusätzliche Information:

Pointer Vs Delegates

+0

Die Frage war, warum es "zu viel Rekursion" in dem anderen Fall macht – ganesshkumar

+0

@Satpal Danke für die Antwort. Können Sie bitte Mozilla-Dokumentationsreferenz auch verweisen. – gvgvgvijayan

+0

@ gvgvgvijayan, Dokumentation für was? – Satpal

1

Wenn Sie () nach dem Namen einer Variablen setzen, eine Funktion zu halten, dann Sie die Funktion nennen.

Wenn sich eine Funktion selbst aufruft, wird sie aufgerufen, ruft sich selbst an, ruft sich selbst wieder an usw. bis zur Unendlichkeit. Das ist Rekursion. Etwas bis unendlich zu tun, wird dazu führen, dass ein Computer keinen Speicher mehr hat, was unerwünscht ist.

JavaScript-Engines verhindern dies, indem Sie beim Versuch eine Ausnahme auslösen.

(Es gibt Ausnahmen, natürlich eine Funktion, die sich bedingt kann very useful sein kann).

1

Der erste Code ist korrekt, weil Sie die aufzurufende Funktion registrieren.

Der zweite Code versucht, das Ergebnis des Funktionsaufrufs once() zu registrieren. Dies bedeutet, dass Sie die Funktion tatsächlich ausführen, wenn Sie sie nur registrieren möchten. In Ihrem Funktionskörper machen Sie jetzt dasselbe, um den Rückruf rückgängig zu machen. Auch hier nennst du die Funktion, die du gerade ausführst, und du rufst unendlich ab.