Fakta JS __proto__ "menyenangkan".

Nov 26 2022
Jika Anda telah mengikuti saya cukup lama, Anda sudah tahu berapa banyak terhadap __proto__ saya selalu begitu, karena itu membuatnya menjadi standar ECMAScript beberapa waktu yang lalu, masih ada kesempatan langka yang saya temukan setidaknya penggunaannya untuk merek sebuah objek dapat diterima: Mengesampingkan kinerja, dan harap dicatat saya tidak menyarankan penggunaan __proto__ sama sekali di alam liar, posting ini ada karena alasan lain. Obyek.
Foto oleh Mark Williams di Unsplash

Jika Anda telah mengikuti saya cukup lama, Anda sudah tahu betapa menentang __proto__saya selama ini, namun, sejak itu membuatnya menjadi standar ECMAScript beberapa waktu yang lalu, masih ada kesempatan langka yang saya temukan setidaknya penggunaannya untuk merek suatu objek dapat diterima :

const factory = (fields, {prototype} = Object) => ({
  __proto__: prototype,
  ...fields
});

// mimic an <a /> reference
factory({href: '/'}, HTMLAnchorElement);

Di Firefox, skor __proto__ lebih baik daripada Kelas baru

Mengesampingkan kinerja, dan harap dicatat saya tidak menyarankan penggunaan __proto__sama sekali di alam liar, posting ini ada karena alasan lain.

Objek.prototipe.__proto__

Saya cukup yakin semua orang tahu apa yang dilakukan __proto__ accessor , jadi saya ingin mengajukan tantangan kepada Anda ... dan ya, ini semua JS yang valid:

class Test {}
const __proto__ = Test.prototype;

// what do these operations return?
({__proto__} instanceof Test);
({__proto__: __proto__} instanceof Test);
({"__proto__": __proto__} instanceof Test);
({["__proto__"]: __proto__} instanceof Test);

// what do these operations return?
({__proto__}.__proto__ === Test.prototype);
({__proto__: __proto__}.__proto__ === Test.prototype);
({"__proto__": __proto__}.__proto__ === Test.prototype);
({["__proto__"]: __proto__}.__proto__ === Test.prototype);

Jika Anda belum menjalankan sendiri cuplikan ini untuk mengetahui jawabannya, saya dapat membantu! Pada tantangan pertama, hasilnya akan menjadi false, true, truedan falselagi, dan alasannya adalah keduanya dan {__proto__}didefinisikan sebagai properti sendiri , sedangkan penugasan melalui sintaks, tanpa menggunakan fitur sintaks khusus, bahkan dengan tanda kutip, sebenarnya melewati accessor.{["__proto__"]}Object.prototype.__proto__

Di sisi lain, dalam tantangan kedua (semua true) tidak masalah jika kita mengakses __proto__secara langsung atau as ["__proto__"], sehingga pada dasarnya tidak ada simetri dalam cara kita dapat memicu __proto__penyetel, dari cara kita dapat memicu __proto__pengambil satu kali itu adalah milik sendiri atau gerbang warisan sihir.

… dan tidak hanya __proto__

Saya belum memeriksanya sendiri, tetapi saya yakin setiap pengakses __xxx__khusus warisan mengalami __proto__kutukan yang sama, jadi harap berhati-hati di luar sana mencampurkan sintaks JS keren terbaru untuk menetapkan properti dengan maksud dan harapan Anda yang sebenarnya, karena hal-hal mungkin dengan mudah menjadi pisang jika Anda mencobanya pintar dalam menetapkan properti ini .

Dan itu semua orang!

Satu-satunya yang diambil dari pos ini kemungkinan diringkas sebagai berikut:

  • jangan gunakan bagian bahasa lama yang belum berfungsi, jika Anda ingin menghindari kejutan hari ini, atau besok, tentang bagaimana ini berperilaku dengan sintaks baru
  • lebih suka eksplisit (dan sayangnya lebih lambat) Object.setPrototypeOfsetiap kali pengaturan prototipe objek secara manual sangat diperlukan, tetapi gunakan kelas dalam setiap kasus lain kapan pun memungkinkan
  • hapus dari memori Anda posting ini atau susutkan menjadi kalimat pendek seperti: " Saya seharusnya tidak pernah menggunakan __proto__kode saya " dan lanjutkan mempelajari hal-hal baru yang mewah yang tidak mengacaukan otak atau perasaan Anda