Satu. Dua prototipe
Banyak orang tahu bahwa JavaScript adalah warisan prototipe. Setiap konstruktor memiliki anggota prototipe, di mana warisan JavaScript bisa indah.
Bahkan, atribut ini saja tidak dapat menyelesaikan warisan JavaScript.
Saya tidak akan banyak bicara tentang prototipe yang kami gunakan dalam kode. Anda dapat memeriksa informasinya.
Anggota prototipe tak terlihat lainnya.
Setiap instance memiliki atribut prototipe yang menunjuk ke prototipe. Atribut ini tidak dapat diakses dan tentu saja tidak dapat dimodifikasi, karena ini adalah dasar untuk mempertahankan warisan JavaScript.
Salinan kode adalah sebagai berikut:
// pernyataan konstruktor
fungsi guoyansi () {}
fungsi guoyansiex () {}
// prototipe warisan
Guoyansiex.prototype = new guoyansi ();
// Buat objek
var g1 = new guoyansiex ();
var g2 = new guoyansiex ();
Objek dalam kode di atas dapat dijelaskan oleh gambar berikut
2. Pemeliharaan prototipe
Contoh yang dihasilkan oleh konstruktor yang atribut konstruktornya selalu menunjuk pada konstruktor. Kami akan berpikir bahwa pernyataan itu benar untuk saat ini.
Salinan kode adalah sebagai berikut:
fungsi guoyansi () {}
var obj1 = Guoyansi baru ();
console.log (obj1.constructor === guoyansi); // true
Faktanya, konstruktor itu sendiri tidak memiliki atribut konstruktor, jadi dari mana atribut ini berasal?
Jawabannya adalah: dari prototipe.
Oleh karena itu, kesimpulan berikut ditarik
Salinan kode adalah sebagai berikut: obj1.constructor === guoyansi.prototype.constructor === Guoyansi
Karena kita dapat menemukan konstruktor melalui konstruktor, kita dapat lebih meningkatkan diagram di atas.
Salinan kode adalah sebagai berikut:
fungsi guoyansiex () {}
Guoyansiex.prototype = new guoyansi ();
console.log (guoyansiex.constructor === GuoyAnsiEx) // false
Menurut gambar di atas, hasil di atas seharusnya benar, tetapi mengapa salah?
Sekarang lakukan analisis.
Prototipe Guoyanix ditulis ulang oleh contoh Guoyansi, sehingga konstruktor dalam prototipe Guoyansix secara alami juga merupakan contoh Guoyansi.
Konstruktor dalam instance Guoyansi berasal dari Guoyansi.prototype. Namun, Guoyansi.Prototype belum ditulis ulang.
Jadi konstruktor Guoyansi.Prototype menunjuk ke Guoyansi (konstruktor);
Berdasarkan analisis di atas, kami menarik kesimpulan berikut
Salinan kode adalah sebagai berikut: GuoyAntieex.Constructor === Guoyansi.Constructor === Guoyansi;
Jika persyaratan arahan konstruktor sangat akurat selama proses pengembangan, pemrosesan berikut dapat dilakukan.
Salinan kode adalah sebagai berikut:
/** Metode 1: **/
fungsi guoyansi () {}
fungsi guoyansiex () {}
Guoyansiex.prototype = new guoyansi ();
GuoyAnsiEx.prototype.constructor = GuoyAntieex; // Reset Pointer Konstruktor.
Salinan kode adalah sebagai berikut:
/**
Metode 2
**/
fungsi guoyansi () {}
fungsi guoyansiex () {
this.constructor = arguments.callee;
}
Guoyansiex.prototype = new guoyansi ();
Salinan kode adalah sebagai berikut:
/**
Metode 3
**/
fungsi guoyansi () {}
fungsi guoyansiex () {
this.constructor = GuoyAntieex;
}
Guoyansiex.prototype = new guoyansi ();
3. Apa gunanya prototipe yang tidak terlihat?
Kami dapat mengoperasikan rantai prototipe yang terlihat untuk menyelesaikan warisan kami, jadi kami tidak dapat melihat dan mengoperasikan rantai prototipe yang tidak terlihat ini. Apa gunanya itu?
Ada fitur dalam warisan berorientasi objek: kesamaan. Subkelas memiliki kesamaan dengan kelas orang tua. Oleh karena itu, dalam subkelas, Anda tidak dapat menggunakan Delete untuk menghapus anggota yang diwarisi dari kelas orang tua. Dengan kata lain, subkelas harus memiliki karakteristik kelas orang tua.
Untuk mempertahankan fitur ini, JavaScript menghasilkan properti prototipe yang tidak terlihat di dalam objek dan tidak mengizinkan pengguna untuk mengaksesnya. Dengan cara ini, pengguna dapat memodifikasi konstruktor untuk tujuan apa pun,
Itu tidak akan menghancurkan karakteristik kelas anak yang memiliki kelas induk.
Singkatnya: Prototipe internal diperlukan oleh mekanisme pewarisan prototipe JavaScript, sementara prototipe eksternal diperlukan oleh pengguna untuk menerapkan warisan.
4. __Proto__ di mesin firefox spidermonkey
Tetap kode ini.
Salinan kode adalah sebagai berikut:
fungsi guoyansi () {}
Guoyansi.prototype.age = 24;
fungsi guoyansiex () {}
var obj1 = Guoyansi baru ();
Guoyansix.prototype = obj1;
GuoyAnsiEx.prototype.constructor = GuoyAntieex; // Reset Pointer Konstruktor.
var obj2 = new guoyansiex ();
Saya sekarang ingin mengakses usia sifat prototipe kelas induk Guoyansi mulai dari OBJ.
Inilah idenya.
Langkah 1: OBJ2 ====> obj2.constructor.prototype
Bagian 2: obj2.constructor.prototype ===> guoyansiex.prototype;
Bagian 3: GuoyAsieex.Prototype ===> OBJ1;
Bagian 4: Obj1.Constructor ====> Guoyansi
Bagian 5: Guoyansi.Prototype.age
Tulis seperti ini: console.log (obj2.constructor.prototype.constructor.prototype.age) // 24;
Hasil akhirnya adalah 24.
Hasil akhirnya adalah 24. Ini dapat dieksekusi secara normal, tetapi dalam banyak buku, dikatakan bahwa setelah konstruktor dimodifikasi, level tidak dapat menemukan prototipe di kelas induk. Saya tidak tahu apa yang sedang terjadi.
Cukup atribut yang lebih ringkas di firefox._proto_
Secara default, Spidermonkey menambahkan atribut yang disebut _proto_ ke objek yang dibuat, yang menunjuk ke prototipe yang digunakan oleh konstruktor.
Faktanya, ini adalah rantai prototipe yang tidak terlihat yang kami sebutkan di atas, tetapi itu hanya pengungkapan yang disamarkan di tempat ini.
Anda dapat mengakses usia dengan cara ini
Console.log (Obj2 .__ Proto __.__ Proto __. Usia); // 24
Ini memang berhasil mengakses atribut prototipe dari kelas induk, tetapi atribut ini hanya berlaku untuk Firefox, dan akan ada kesalahan di browser lain.
Di E5, objek diperluas ke objek.getPrototypeOf (), dan Anda dapat mengakses semua prototipe kelas induk.
Salinan kode adalah sebagai berikut:
fungsi guoyansi () {}
Guoyansi.prototype.age = 24;
fungsi guoyansiex () {}
var obj1 = Guoyansi baru ();
Guoyansix.prototype = obj1;
GuoyAnsiEx.prototype.constructor = GuoyAntieex; // Reset Pointer Konstruktor.
var obj2 = new guoyansiex ();
var proto = objek.getPrototypeOf (obj2);
while (proto) {
console.log (proto.constructor);
proto = objek.getPrototypeOf (proto);
}
console.log ("Prototipe Object"+Proto);
Hasilnya adalah: GuoyAsiex
Guoyansi
Obyek
Prototipe nol untuk objek
Saya pribadi berpikir ini harus dianggap sebagai salah satu esensi javascript yang berorientasi objek. Silakan merujuknya sendiri dan menggunakannya dalam proyek Anda sendiri sesuai dengan kebutuhan Anda.