2016-07-11 40 views
7

Questo codice ES6:Utilizzando lo stesso nome argomento come parametro predefinito in ES6

const log =() => console.log('hi'); 
const parent = (log = log) => log(); 
parent(); 

Transpiled a:

var log = function log() { 
    return console.log('hi'); 
}; 
var parent = function parent() { 
    var log = arguments.length <= 0 || arguments[0] === undefined ? log : arguments[0]; 
    return log(); 
}; 
parent(); 

dà l'errore:

return log(); 
     ^
TypeError: log is not a function 

Il problema è questa linea:

const parent = (log = log) => log(); 

Poiché il nome dell'argomento è uguale al parametro predefinito.

questo funziona:

const log =() => console.log('hi'); 
const parent = (logNow = log) => logNow(); 
parent(); 

È questo un bug in Babel o si tratta di non ammessi nelle specifiche per sé?

+1

sollevamento provoca questo problema. –

risposta

3

Sembra che questo è il comportamento previsto di ES6. Testato sulla console di Chrome, anche un errore.

Le specifiche ES6 sta dicendo a quel punto:

  1. Let parameterNames be the BoundNames of formals. http://www.ecma-international.org/ecma-262/6.0/#sec-functiondeclarationinstantiation

Questo significa che quando si crea la funzione, ES6 farà fondamentalmente la stessa babel, come sta facendo, esso gestirà l'assegnazione delle params nel nuovo contesto .

in JavaScript, quando si crea una variabile a in un ambito chiuso, globale a, non è possibile accedere più, perché JS prenderà il a dal campo di applicazione più vicino possibile, in AST.

semplice esempio:

var a = 1; 
function test() { 
    // creates the variable a, and try to assign a value to it, 
    // because `a` is now available in the scope itself, it will take value of a in the inner scope, not the outer scope one 
    var a = a; 
    console.log(a) 
} 
test() // undefined 

Perché la sua non prendendo il valore di esterno una, e quindi assegnare al un interno, è a causa della sollevamento, in fondo il suo fare questo:

function test() { 
    var a; // the address for the variable is reserved at compile time 
    a = a; // run-time assignment 
} 

Accetta tutte le dichiarazioni delle variabili di una funzione e la solleva all'inizio della funzione.

Questo è il motivo, per cui qualcosa di simile a questo lavoro:

function hoistingTest(n, m = 2) { 
    // return immediately 
    return multi(n); 

    // This declaration will be hoisted to the begin of the body 
    function multi(n) { return m * n } 
} 
+0

E puoi semplicemente copiare il codice originale nella console di Chrome e si comporterà come dice questa risposta, se vuoi una prova veloce –

Problemi correlati