2017-05-20 10 views
1

Bin ein bisschen ein Autodidakt JS-Hack und versucht, ein wenig formeller zu sein, wie ich eine besser benommene JS-Anwendung bauen muss, die Namens-Abstand und eine bessere JS-Bürger ist. Ich würde gerne einige Hinweise darauf, was ich hier falsch mache, schätzen.Unerwartete Sequenz der IIFE-Ausführung

Die Idee ist es, die erste Schließung zu verwenden, um einen Namespace zu konstruieren, dann in der zweiten füge ich eine Methode ein 'Klasse' Konstruktor zum Namespace-Objekt. Das rufe ich eine Methode auf dem Sub.

(function() { 
 
    'use strict'; 
 
    /** 
 
    * @namespace ProjectX 
 
    */ 
 

 
    var ProjectX = { 
 

 
     attr1: 'I am inside ProjectX' 
 
     
 
    } 
 
    window.ProjectX = ProjectX; 
 

 
})() 
 

 
//console.log(ProjectX.attr1); // When this line is uncommented the code will output 'foobar' as expected? 
 

 
(function() { 
 
    'use strict'; 
 

 
    ProjectX.subObj = function(val) { 
 
     this.name = val; 
 
     return this; 
 
    }; 
 
})(); 
 

 

 
var subObj = new ProjectX.subObj('Foobar'); 
 
console.log(subObj.name);

Ich erwarte 'Foobar' in dem Konsolenprotokoll zu sehen. Jedoch ergibt dies das folgende Ergebnis in der Konsole:

{ "message": "Uncaught TypeError: (intermediate value)(intermediate value)(intermediate value)(...) is not a function", "filename": " http://stacksnippets.net/js ", "lineno": 03, "colno": 1 }

Wenn ich diesen Code lesen Ich gehe davon aus, dass die beiden IIFE die in Folge ausgeführt wird, wobei die erste ProjectX zum Leben zu erwecken, dann die zweite einen weiteren Konstruktor ProjectX fügte hinzu, dass wird ein subObj zurückgeben. Wenn die console.log ((ProjectX.attr1) in Zeile 16 unkommentiert ist, wird der Code wie erwartet ausgeführt. Dies scheint darauf hinzudeuten, dass die ProjectX-Entity erst dann "präsent" ist, wenn ich sie referenziert habe. Dies widerspricht Mein Verständnis von IIFE, das ist, dass sie sofort ausgeführt werden, und sowieso, ProjectX ist kein Konstruktor - es ist eine globale Variable.

In der Forschung fand ich function inside of IIFE not recognized, die scheint, ähnlich zu sein Gebiet, aber mit einer Bindung zu einem Ereignis verbunden ist das DOM und nicht eine Parallele zu meiner Abfrage

+1

Sie verpassen ein Semikolon nach dem ersten IIFE, was relevant wird, wenn die console.log mit ihrem Semikolon entfernt wird. Sie können nach den Fällen suchen, in denen Semikolons in JS benötigt werden. Sie könnten auch versuchen, es6 mit babel zu verwenden, um Ihren Code besser zu organisieren und bessere Lesbarkeit zu haben. – sabithpocker

+0

Danke @sabithpocker.Zu ES6 Ich muss aktuelle gängige Browser abdecken und ich glaube, ES6 ist noch nicht vollständig abgedeckt. –

+1

Versuchen Sie [Babel] (https://babeljs.io) – sabithpocker

Antwort

3

Ihnen fehlt ein Semikolon nach dem ersten IIFE, was relevant wird, wenn die console.log mit dem Semikolon entfernt wird.Sie können nach den Fällen suchen, in denen in JS

Semikolons benötigt werden

Ohne Semikolon, kann Ihr Code wie interpretiert werden:

(function() { 
    var ProjectX = { 
     attr1: 'I am inside ProjectX' 
    } 
    window.ProjectX = ProjectX; 
})()(function() { 
    ProjectX.subObj = function(val) { 
     this.name = val; 
     return this; 
    }; 
})(); 

Überprüfen Sie die folgende Funktion (IIFE)()() im Format, das funktioniert, weil IIFE eine Funktion gibt, die mit ('Hey')

(function() { 
 
     return function(msg){console.log(msg)} 
 
    })()('Hey')
aufgerufen wird

Ohne Semikolon erwartet Javascript, dass Ihre erste IIFE eine Funktion zurückgibt, die nicht die c ist ase mit Ihrem Code, so dass es einen Typfehler gibt, der besagt, dass es eine Funktion erwartet, aber nicht definiert wurde. Ihr Code wertet schließlich zu:

undefined(function() { 
    ProjectX.subObj = function(val) { 
     this.name = val; 
     return this; 
    }; 
})(); 

oder mehr vereinfacht als

undefined(<a function as parameter>)() 

die dann den Fehler auslöst, dass ein function erwartet wird hier statt undefined.

Lesen Sie über Funktionen höherer Ordnung in Javascript, um eine bessere Vorstellung von dieser Syntax zu bekommen und zu dem, was Ihr Code mehrdeutig ist.

+0

Nur um dies zu bestätigen, sieht JS dies als etwas wie()()()() welches es von rechts nach links auflöst? Daher wurde das erste IIFE nicht vor dem zweiten evaluiert, zu diesem Zeitpunkt ist ProjectX nicht definiert. Richtig ? –

+0

Nein, das ist nicht richtig, es hat nichts mit der Definition von ProjectX zu tun. 'myFunction()()()' wird mehr von links nach rechts als von rechts nach links ausgewertet. Ich werde versuchen, die Antwort zu aktualisieren, um weitere Details hinzuzufügen. – sabithpocker

Verwandte Themen