Menu

Parâmetros Padrão em JavaScript: Valores Default em Funções

Entenda como funcionam os parâmetros em JavaScript: valores padrão, o papel do undefined, ordem de avaliação e a diferença entre parâmetros e argumentos.

Parâmetros e argumentos: qual a diferença?

Duas palavras que a galera vive confundindo. Parâmetro é o nome que aparece na definição da função. Argumento é o valor que você passa na hora de chamar. A ideia é a mesma do Python e da maioria das linguagens:

index.js
Output
Click Run to see the output here.

a e b são parâmetros. Já 2 e 3 são argumentos. O JavaScript faz a ligação por posição: o primeiro argumento vai para o primeiro parâmetro, e assim por diante. Pode parecer uma diferença sutil, mas é o vocabulário que aparece nas mensagens de erro e na documentação da MDN.

JavaScript é flexível com a quantidade de argumentos

Diferente de muitas outras linguagens, o JavaScript não reclama se você passa argumentos demais ou de menos. Parâmetros que ficam sem valor viram undefined, e os argumentos que sobram são simplesmente ignorados:

index.js
Output
Click Run to see the output here.

A primeira chamada imprime Olá, Ada undefined — como last não recebeu valor, ele fica como undefined, e o template literal interpola isso sem reclamar. Nada de erro, nada de warning. Essa flexibilidade às vezes ajuda, às vezes vira fonte de bug — e é justamente por isso que os parâmetros padrão existem.

Definindo um valor padrão

Basta colocar = e um valor depois do nome do parâmetro. Se quem chamou a função não passar aquele argumento (ou passar undefined), o valor default entra em ação:

index.js
Output
Click Run to see the output here.

As três chamadas funcionam. A primeira e a terceira disparam o valor padrão; a segunda usa o valor que foi passado. Essa sintaxe é do ES6 — antes de 2015, tinha que escrever name = name || "friend" dentro do corpo da função, o que trazia seus próprios bugs com valores falsy como 0 e "".

O valor default pode ser qualquer expressão, não só literais:

index.js
Output
Click Run to see the output here.

A expressão é avaliada a cada chamada, e não uma única vez quando a função é definida. Ou seja, nada daquela armadilha de default mutável que existe em Python — cada chamada recebe um new Date() novinho.

undefined dispara o valor padrão

Essa é a regra que pega muita gente de surpresa. O parâmetro padrão só entra em ação quando o argumento é undefined — não quando ele é falsy e nem quando é null:

index.js
Output
Click Run to see the output here.

Só a última chamada usa "friend". Quando você passa null de forma explícita, está dizendo "o valor é null" — e o JavaScript leva isso ao pé da letra. O mesmo vale para strings vazias e zeros: são valores de verdade, não argumentos ausentes.

Se quiser que null seja tratado como ausente, você precisa cuidar disso na mão:

index.js
Output
Click Run to see the output here.

O operador ?? (coalescência nula) trata tanto null quanto undefined como "ausente". Falaremos mais sobre isso em um capítulo posterior.

Valor padrão baseado em outro parâmetro

Os parâmetros são avaliados da esquerda para a direita, então um valor padrão pode usar qualquer parâmetro que tenha sido declarado antes dele:

index.js
Output
Click Run to see the output here.

Uma chamada com apenas um argumento gera um cubo. Com dois argumentos, você tem um prisma de base quadrada. A ordem importa — não dá pra referenciar um parâmetro que ainda não foi declarado:

function bad(a = b, b = 1) {
  return a + b;
}

bad();   // ReferenceError: Cannot access 'b' before initialization

Mesmas regras das variáveis declaradas com let: usar antes de declarar gera erro.

Valores padrão com desestruturação

Dá pra desestruturar parâmetros e já definir valores padrão na mesma linha. Esse é um padrão bem comum quando a função recebe um "objeto de opções" como argumento:

index.js
Output
Click Run to see the output here.

Há duas camadas de valores padrão em ação aqui. As internas (role = "member", active = true) preenchem propriedades que não foram informadas. Já o = {} externo cobre o caso em que quem chama não passa argumento nenhum — sem ele, createUser() tentaria desestruturar undefined e estouraria um erro.

À primeira vista o padrão parece carregado, mas ele aparece o tempo todo em bases de código JavaScript modernas. Depois que seu olho se acostuma a enxergar { ... } = {} como "opções com valores padrão", a leitura flui rápido.

Pulando um argumento do meio

O JavaScript não tem argumentos nomeados como o Python. Para pular um parâmetro do meio e usar seu valor default, você precisa passar undefined de forma explícita:

index.js
Output
Click Run to see the output here.

Passar undefined em prefix preserva o valor padrão. Fica feio. Se você perceber que está escrevendo undefined nas chamadas com frequência, é sinal de que vale a pena migrar para um objeto de opções:

index.js
Output
Click Run to see the output here.

Agora quem chama a função diz exatamente o que quer sobrescrever, e a ordem deixa de importar.

Valores padrão não contam no length

Um detalhe pequeno que quase nunca faz diferença, mas de vez em quando pega alguém desprevenido. A propriedade length de uma função retorna a quantidade de parâmetros antes do primeiro que tem valor padrão:

index.js
Output
Click Run to see the output here.

Bibliotecas que inspecionam funções (como algumas ferramentas de teste e de injeção de dependência) usam length para contar os parâmetros "obrigatórios". É bom saber que essa regra existe, mas não vale a pena decorar — a não ser que você esteja escrevendo esse tipo de ferramenta.

A seguir: Rest e Spread

Os valores padrão resolvem o caso em que você já conhece os parâmetros de antemão. Mas às vezes isso não acontece — você quer que a função aceite um número qualquer de argumentos, ou então repassar um monte de argumentos para outra função. É aí que entram o ...rest e o operador spread, que vêm logo na sequência.

Perguntas frequentes

Como definir um valor padrão para um parâmetro em JavaScript?

Basta usar = e o valor padrão logo após o nome do parâmetro na assinatura da função: function greet(name = 'friend') { ... }. Se quem chama não passar valor nenhum (ou passar undefined), o default entra em ação. É sintaxe do ES6 e funciona em qualquer ambiente moderno de JavaScript.

Qual a diferença entre parâmetro e argumento?

Parâmetros são os nomes que aparecem na definição da função — em function add(a, b), os parâmetros são a e b. Argumentos são os valores que você passa na hora da chamada — em add(2, 3), os argumentos são 2 e 3. Essa distinção ajuda muito na hora de ler mensagens de erro e documentação.

O valor padrão é aplicado quando eu passo null?

Não. O default só dispara quando o argumento é undefined (ou quando nem é passado). Passar null explicitamente significa 'estou te dando um valor, e esse valor é null' — o padrão é ignorado. Isso costuma confundir quem vem de linguagens onde null e undefined são a mesma coisa.

Um valor padrão pode usar outro parâmetro?

Pode. Os parâmetros são avaliados da esquerda para a direita, então o default de um parâmetro posterior pode referenciar os anteriores: function box(width, height = width). Dá até para chamar funções no default — function log(msg, time = Date.now()) — e a expressão é executada a cada chamada.

Aprenda a programar com o Coddy

COMEÇAR