Ruby || = (atau sama dengan) di JavaScript?

128

Saya suka ||=mekanisme Ruby . Jika variabel tidak ada atau ada nil, buatlah dan setel sama dengan sesuatu:

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

Saya perlu melakukan sesuatu yang serupa di JavaScript sekarang. Apa konvensi atau cara yang tepat untuk melakukan ini? Saya tahu ||=itu bukan sintaks yang valid. 2 cara yang jelas untuk menanganinya adalah:

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

// or

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

Jawaban:

152

Keduanya benar-benar benar, tetapi jika Anda mencari sesuatu yang berfungsi seperti ||=di ruby. Metode pertama yang variable = variable || {}Anda cari :)

Dzung Nguyen
sumber
1
Hati-hati menggunakan ini jika nilai yang valid xadalah falsy, like false, dan Anda hanya ingin menyetel default saat xtidak ditentukan.
Joshua Pinter
komentar di atas benar. Mengambil contoh kasus Anda, ini tidak akan bekerja dengan cara yang sama di JS. let amount = 0;diikuti oleh amount = amount || 5 akan berubah menjadi 5. Jika Anda tidak ingin hal itu terjadi gunakan ??operator sebagai gantinya ||.
AshwinKumarS
@AshwinKumarS Atau cukup gunakan amount ??= 5;.
user4642212
@ user4642212 Saya tidak berpikir bahwa sintaks bekerja di JS, bukan?
AshwinKumarS
@AshwinKumarS Ya, benar. Lihat dokumentasi , spesifikasi , proposal .
user4642212
22

Anda dapat menggunakan operator OR logis ||yang mengevaluasi operan kanannya jika lValnilai salah.

Nilai-nilai yang salah termasuk misalnya null, false, 0, "", undefined, NaN

x = x || 1
Moritz Roessler
sumber
Hati-hati menggunakan ini jika nilai yang valid xadalah falsy, like false, dan Anda hanya ingin menyetel default saat xtidak ditentukan.
Joshua Pinter
4

Jika Anda bekerja dengan objek, Anda dapat menggunakan destructuring (sejak ES6) seperti ini:

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

... tetapi Anda tidak mendapatkan apa-apa atas jawaban yang diterima kecuali kebingungan.

Firasat
sumber
1
"tetapi Anda tidak mendapatkan apa-apa atas jawaban yang diterima kecuali kebingungan" - bagus. :)
lindes
Saya yakin seseorang akan menganggap ini sebagai alasan untuk membenci javascript
Volper
1

Operator yang Anda tanyakan telah diusulkan sebagai fitur dalam JavaScript . Saat ini berada di Tahap 3 , jadi belum menjadi bagian resmi dari bahasa tersebut, tetapi akan diterima, dengan paling banyak perubahan kecil jika mereka menemukan masalah besar yang tidak terduga.

Anda dapat menggunakannya sekarang menggunakan plugin Babel plugin-proposal-logical-assignment-operator . Saya belum pernah menggunakan plugin itu, jadi saya tidak tahu seberapa baik kerjanya.

Elias Zamaria
sumber
-1

Ruby || = tugas hubung singkat operator. Ini dapat dianggap seperti ini:

return a || a = b

Jadi di javascript, ini terlihat sangat mirip:

return a || (a = b);

Namun, tampaknya seperti yang ditunjukkan pada komentar di bawah, bentuk literal ruby ​​ini kurang efisien dibandingkan dengan idiom javascript standar a = a || b.

Untuk referensi: http://www.rubyinside.com/what-rubys-double-pipe-or-equals-really-does-5488.html

chris
sumber
1
Dalam praktiknya, tampaknya a = a || bbentuknya lebih optimal jsperf.com/x-or-x-equals-0-vs-x-equals-x-or-0/3
jchook
ah alat yang keren. bagaimana jadinya jika x memiliki nilai dan jadi hubung singkat?
chris
Saya percaya pembongkaran harus eksplisit pada jsperf sehingga tes ini harus menunjukkan kinerja korsleting. Dugaan saya adalah bahwa V8 memiliki pengoptimalan khusus untuk formulirnya a = a || b.
jchook
3
FYI Sepertinya apa pun perbedaan yang ada sekarang telah dioptimalkan.
Charles Wood
a || (a = b)memiliki semantik yang benar untuk menyimpulkan nama fungsi. Saat ini sedang dalam diskusi untuk proposal baru.
user4642212
-1

Anda dapat mencapai perilaku yang diinginkan menggunakan | = operator di javascript hanya untuk bilangan bulat. Tetapi Anda harus mendefinisikan variabel terlebih dahulu.

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

Untuk benda

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

Untuk Array

let arr = []
arr[0] |= 100
console.log(arr) // [100]
Wallgeek
sumber
Pertanyaannya bukan tentang |atau |=. Perilaku yang diinginkan dalam pertanyaan tidak terkait dengan operasi bitwise.
pengguna4642212
Anda benar, saya akan mengedit jawabannya sesuai
wallgeek
Diedit. Saya harap ini masuk akal sekarang.
wallgeek