2015-08-28 2 views
67

eine Eingabedatei wieWarum schreibt Babel den importierten Funktionsaufruf auf (0, fn) (...) um?

import { a } from 'b'; 

function x() { 
    a() 
} 

babel es

'use strict'; 

var _b = require('b'); 

function x() { 
    (0, _b.a)(); 
} 

zu

aber wenn in losen Modus der Funktionsaufruf ausgegeben _b.a();

als kompilierte kompiliert Da ich einige der Forschung in getan habe wo der Komma-Operator hinzugefügt wird in der Hoffnung, dass es einen Kommentar gab, der es erklärte. Der für das Hinzufügen verantwortliche Code ist here.

+3

Sie sollten '_b.a.call()' gemacht haben, um die Absicht klar zu machen. – Bergi

+0

@Bergi Ich bin sicher, der Grund, warum sie es mit (0,) ist, ist Speicherplatz im transpiled Code zu sparen. – Andy

+2

siehe auch [Beeinflusst der Komma-Operator den Ausführungskontext in Javascript?] (Http://stackoverflow.com/q/36076794/1048572) – Bergi

Antwort

93

(0, _b.a)() stellt sicher, dass die Funktion _b.a mit this auf das globale Objekt gesetzt genannt wird (oder wenn Strict-Modus aktiviert ist, zu undefined). Wenn Sie _b.a() direkt anrufen möchten, wird _b.a mit this auf aufgerufen.

(0, _b.a)(); äquivalent zu

0; // Ignore result 
var tmp = _b.a; 
tmp(); 

(die , ist der Komma-Operator, siehe https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Comma_Operator).

+2

danke für den Link. so oft übergangen und beschlossen, herauszufinden, was passiert ist. –

+0

@RobW Ich denke, das Hinzufügen von 'var _a = (0, _b.a)' am Anfang der Datei und das Aufrufen von '_a' würde in vielen Fällen mehr Speicherplatz sparen, jede Idee, dass sie das nicht getan haben? – Andy

+1

@Andy Ihr Vorschlag kann Nebenwirkungen haben, z.B. wenn '_b.a' ein (dynamischer) Getter ist. –

9

Der Kommaoperator wertet jeden seiner Operanden (von links nach rechts) aus und gibt den Wert des letzten Operanden zurück.

console.log((1, 2)); // Returns 2 in console 
console.log((a = b = 3, c = 4)); // Returns 4 in console 

Also, lassen Sie ein Beispiel sehen:

var a = { 
    foo: function() { 
    console.log(this === window); 
    } 
}; 

a.foo(); // Returns 'false' in console 
(0, a.foo)(); // Returns 'true' in console 

nun in foo Verfahren, this gleich a (weil foo-a angeschlossen ist). Wenn Sie also direkt a.foo( anrufen, wird false in der Konsole protokolliert.

Aber, wenn Sie (0, a.foo)() anrufen würden. Der Ausdruck (0, a.foo) wertet jeden seiner Operanden aus (von links nach rechts) und gibt den Wert des letzten Operanden zurück. Mit anderen Worten, ist (0, a.foo) entspricht

function() { 
    console.log(this === window); 
} 

Da diese Funktion nicht mehr an alles gebunden ist, seine this ist das globale Objekt window. Deshalb loggen Sie sich true in der Konsole ein, wenn Anruf (0, a.foo)().