Ruby || = (ou igual) em JavaScript?


128

Eu amo o ||=mecanismo de Ruby . Se uma variável não existir ou for nil, crie-a e defina-a como algo:

amount # is nil
amount ||= 0 # is 0
amount ||= 5 # is 0

Eu preciso fazer algo semelhante em JavaScript agora. Qual é a convenção ou a maneira correta de fazer isso? Eu sei que ||=não é uma sintaxe válida. 2 maneiras óbvias de lidar com isso são:

window.myLib = window.myLib || {};

// or

if (!window.myLib)
  window.myLib = {};

Respostas:


152

Ambos estão absolutamente corretos, mas se você estiver procurando por algo que funcione como ||=em rubi. O primeiro método variable = variable || {}é o que você está procurando :)


Cuidado ao usar isso se um valor válido para xfor falso, como false, e você desejar definir um padrão quando xindefinido.
Joshua Pinter

22

Você pode usar o operador OR lógico ||que avalia seu operando correto se lValfor um valor falso.

Os valores de falsidade incluem, por exemplo, null, false, 0, "", undefined, NaN

x = x || 1

Cuidado ao usar isso se um valor válido para xfor falso, como false, e você desejar definir um padrão quando xindefinido.
Joshua Pinter

4

Se você estiver trabalhando com objetos, poderá usar a desestruturação (desde o ES6) da seguinte forma:

({ myLib: window.myLib = {} } = window);

... mas você não ganha nada sobre a resposta aceita, exceto confusão.


1
"mas você não ganha nada sobre a resposta aceita, exceto confusão" - legal. :)
lindes 7/04

Aposto que alguém vai levar isso como uma razão para odiar javascript
Volper


-1

Ruby || = atribuição de curto-circuito do operador. Pode-se pensar assim:

return a || a = b

Então, em javascript, isso parece muito semelhante:

return a || (a = b);

Parece, como indicado nos comentários abaixo, no entanto, que esse formato literal de rubi é menos eficiente que o idioma javascript padrão a = a || b.

Para referência: http://www.rubyinside.com/what-rubys-double-pipe-or-equals-really-does-5488.html


1
Na prática, parece que a a = a || bforma é mais ideal jsperf.com/x-or-x-equals-0-vs-x-equals-x-or-0/3
jchook

ah ferramenta legal. como é se x tem um valor e tem um curto-circuito?
chris

Acredito que a desmontagem precisa ser explícita no jsperf, portanto, este teste deve mostrar o desempenho do curto-circuito. Meu palpite é que o V8 tem uma otimização especial para o formulário a = a || b.
jchook

3
Para sua informação, parece que qualquer diferença que tenha sido agora foi otimizada.
Charles Wood

a || (a = b)possui a semântica correta para inferir nomes de funções. Está atualmente em discussão para a nova proposta.
user4642212

-1

Você pode obter o comportamento desejado usando o operador | = em javascript apenas para números inteiros. Mas você precisa definir a variável primeiro.

let a = 0
a |= 100
console.log(a) // 100

Para objetos

let o = {}
o.a |= 100
console.log(o) // {a: 100}

Para matrizes

let arr = []
arr[0] |= 100
console.log(arr) // [100]

A questão não é sobre |ou |=. O comportamento desejado na pergunta não está relacionado às operações bit a bit.
user4642212 16/07

Você está certo, eu vou editar a resposta de acordo.
wallgeek 16/07

Editado. Espero que faça sentido agora.
wallgeek
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.