Funções Javascript e parâmetros padrão, não funcionam no IE e Chrome

101

Eu criei uma função como esta:

function saveItem(andClose = false) {

}

Funciona bem no Firefox

No IE, ocorre este erro no console: Expected ')'

No Chrome, dá este erro no console: Uncaught SyntaxError: Unexpected token =

Ambos os navegadores marcam a origem do erro como a linha de criação da função.

Talon
fonte
Navegador de estoque Android 5.1.1 aqui, mesmo problema.
jc

Respostas:

149

Você não pode fazer isso, mas pode fazer algo como:

function saveItem(andClose) {
   if(andClose === undefined) {
      andClose = false;
   }
}

Geralmente é abreviado para algo como:

function setName(name) {
  name = name || 'Bob';
}

Atualizar

O acima é verdadeiro para ECMAScript <= 5. ES6 propôs parâmetros padrão . Portanto, o acima poderia ser:

function setName(name = 'Bob') {}
Juco
fonte
14
Isso é útil para o IE11 e inferior, que não implementa ES6 e interrompe os parâmetros padrão.
Eran Goldin
2
Obrigado!! Não sabia disso! O IE é péssimo, mas os desenvolvedores não têm outra escolha a não ser oferecer suporte a um navegador "não".
Fr0zenFyr
4
name = name || 'Bob';não deve ser usado porque se o nome for definido com um valor falsey, o padrão será usado no lugar do nome
Gerard Simpson
8
Em vez de name = name || 'Bob'usar name = (name === undefined) ? '' : name;
Brian
1
@juco Não entendo "Você não pode fazer isso" - Mozilla MDN diz que podemos? developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/… Você está apenas dizendo que não pode fazer isso no IE ou está dizendo que os documentos do Mozilla são imprecisos?
php-b-grader
13

Essa não é uma sintaxe ECMAScript válida, mas é uma sintaxe válida para o superconjunto de recursos do Mozilla que eles adicionam à implementação da linguagem.

A sintaxe de atribuição de parâmetro padrão provavelmente vem no ECMAScript 6.

o sistema
fonte
1
Ok, então qual é a melhor maneira de definir os valores padrão nas funções Javascript?
Talon,
1
@Talon: A melhor maneira depende da sua situação. Se você sabe que o argumento não será falso, você pode fazer foo = foo || "the default". Ou você pode verificar o .lengthdo argumentsobjeto. Ou você pode simplesmente testar cada parâmetro para undefined. Existem diferentes ocasiões para usar cada um.
o sistema de
8

Javascript não permite um especificador "padrão".

Uma maneira rápida de fazer o que você gostaria é mudando:

function saveItem(andClose = false) {

}

para o seguinte:

function saveItem(andClose) {
    // this line will check if the argument is undefined, null, or false
    // if so set it to false, otherwise set it to it's original value
    var andClose = andClose || false;

    // now you can safely use andClose
    if (andClose) {
        // do something
    }
}
JRomero
fonte
1
será definido andClosecomo falso, foi 0 ... não é bem o que eu esperava ...
gdoron está apoiando Monica
@gdoron veja isto: stackoverflow.com/questions/7615214/… essas são as peculiaridades que você precisa aprender sobre qualquer linguagem que usar.
JRomero
uma alternativa é alterar a terceira linha para var andClose = andClose === undefined? false: andClose;Isso permitirá que você passe 0para a função e não a substitua por false.
Max Heiber
2

O código fornecido não será executado no Chrome <versão 49: https://kangax.github.io/compat-table/es6/#test-default_function_parameters

Você usou a sintaxe ECMAScript 2015 válida:

Na minha opinião, a melhor maneira de usar os recursos do ES2015 é agrupar os ativos com o Browserify ou WebPack , com uma etapa para usar o Babel para trans-compilar o ES2015 para o ES5. Dessa forma, você não precisa se preocupar com o gráfico de compatibilidade do navegador ES2015. É uma pena começar da primeira vez, mas vale a pena.

Max Heiber
fonte
0

No seu caso, você tem outra alternativa para garantir que sua variável seja booleana:

function saveItem(andClose) {
  var andClose = true == andClose;
  // ...
}

O valor padrão é undefined, e true == undefined=> false, então seu valor padrão será false:)

Cédric Talpaert
fonte
Um pequeno ajuste seria remover a declaração var, pois a andClosevariável já está atribuída neste escopo
Ben Sewards