2017-09-04 1 views
2

schätzen würde wissen, warum dieser Ausdruck:Ausgewertet Ausdruck const variable Umfang in Safari

eval("const a = function() {}; function b() { a(); }; b();") 

einen Fehler auslöst, wenn in Safari 10.1.2 laufen:

ReferenceError: Can't find variable: a

+1

Da Safari ist der neue Internet Explorer –

Antwort

2

Ich vermute, dass die Verwendung von const (oder let) setzen Sie diese Variable in einen internen Bereich von eval, während Funktionen, die innerhalb eval genannt werden, verwenden:

  1. globaler Gültigkeitsbereich, wenn sie durch function X(){} definiert wurden;
  2. internen Bereich, wenn sie als const X = function(){} definiert wurden.

Zum Beispiel mit const:

> eval('const a = function(){ return 42; }; a();') 
42 
> a 
ReferenceError: Can't find variable: a 

Mit var:

> eval('var a = function(){ return 42; }; a();') 
42 
> a 
function(){ return 42; } 

Zur Untermauerung dieser Theorie:

> eval('const a=function(){return 42;}; const b=function(){return a();}; b();') 
42 
> a 
ReferenceError: Can't find variable: a 
> b 
ReferenceError: Can't find variable: b 

Also, es funktioniert, wenn wir beide Funktionen auf die gleiche Weise definieren.

Nun lassen Sie uns Funktion a in globalen Bereich definieren tun, ohne eval mit:

> a = function(){ return 23;} 

Und lassen Sie uns eval Code aus Ihrer Frage (Hinzufügen return s für beide Funktionen) laufen:

> eval("const a = function(){return 42;}; function b(){return a();}; b();") 
23 

Wie Sie sehen können, verwendet die Funktion b den globalen Bereich a.

+0

Großartig! Aus irgendeinem Grund erzeugt Safari keine Schließung für die Funktion "b" mit den lokalen Variablen, die während "eval()" definiert wurden, was für Chrome anders ist. Ich bin mir nicht sicher, was das richtige Verhalten ist, verdammte du Safari, um meine Zeit zu verschwenden! – agoldis