JavaScriptの深く入り込むのは原型から原型の鎖までです.


JavaScriptはシリーズの第一編に深く入り込んでいます.プロトタイプとプロトタイプチェーンからお話します.コンストラクションの実例の原型、プロトタイプ、プロトタイプの原型は何ですか?この文章を見てみましょう.
コンストラクタの作成
まず、構造関数を使ってオブジェクトを作成します.
function Person() {

}
var person = new Person();
person.name = 'Kevin';
console.log(person.name) // Kevin
この例ではPersonは構造関数であり,newを用いて例示的なオブジェクトpersonを作成した.
簡単ですよね.次は本題に入ります.
プロトタイプ
各関数にはプロトタイプの属性があります.つまり、私たちがよくいろいろな例で見たプロトタイプです.
function Person() {

}
//        ,      :
// prototype         
Person.prototype.name = 'Kevin';
var person1 = new Person();
var person2 = new Person();
console.log(person1.name) // Kevin
console.log(person2.name) // Kevin
この関数のプロトタイプの属性は一体何を指していますか?この関数の原型ですか?
実は、関数のプロトタイプ属性はオブジェクトを指しています.このオブジェクトはこのコンストラクタを呼び出して作成された例のプロトタイプです.つまりこの例のperson 1とperson 2のプロトタイプです.
原型は何ですか?JavaScriptオブジェクトごとに(nullを除く)作成時に別のオブジェクトに関連します.このオブジェクトは私たちが言っているプロトタイプです.どのオブジェクトもプロトタイプから属性を継承します.
構造関数と実例の原型の関係を一枚の図で表しましょう.
この図では例のプロトタイプをObject.prototypeで表します.
実例と実例の原型、つまりpersonとPerson.prototypeの関係をどう表しますか?
同前プロト.
これは各JavaScriptオブジェクト(nullを除く)が持つ属性の一つです.proto_,この属性はそのオブジェクトの原型を指します.
この点を証明するために、火狐またはGoogleに入力できます.
function Person() {

}
var person = new Person();
console.log(person.__proto__ === Person.prototype); // true
そこで私たちは関係図を更新します.
例のオブジェクトと構造関数がプロトタイプに向けられるなら、プロトタイプは構造関数またはインスタンスに向けられていますか?
トラック
指差の例はないですが、一つのコンストラクタは複数のインスタンスを生成することができますが、プロトタイプはコンストラクタを指しています.これは第三の属性を述べます.
この点を検証するために、試してみてもいいです.
function Person() {

}
console.log(Person === Person.prototype.constructor); // true
だからまた関係図を更新します.
以上より、私達はすでに結論を出しました.
function Person() {

}

var person = new Person();

console.log(person.__proto__ == Person.prototype) // true
console.log(Person.prototype.constructor == Person) // true
//       ES5   ,         
console.log(Object.getPrototypeOf(person) === Person.prototype) // true
構造関数、インスタンスプロトタイプ、およびインスタンス間の関係を理解しました.次に実例とプロトタイプの関係を説明します.
実例と原型
インスタンスのプロパティを読み込むと、オブジェクトに関連するプロトタイプの属性が見つからない場合は、まだ検出されていない場合は、プロトタイプのプロトタイプを探して最上階まで探します.
例を挙げます
function Person() {

}

Person.prototype.name = 'Kevin';

var person = new Person();

person.name = 'Daisy';
console.log(person.name) // Daisy

delete person.name;
console.log(person.name) // Kevin
この例では、私たちはインスタンスオブジェクトのpersonにname属性を追加しました.私たちがperson.nameを印刷すると、結果は自然にDaisyです.
しかし、私たちはpersonのname属性を削除した時、person.nameを読み、personオブジェクトからname属性が見つからないと、personのプロトタイプ、つまりperson._._._._.u.u.proto_,つまりPerson.prototypeで探してみます.幸いなことに、私たちはname属性を見つけました.結果はKevinです.
でももしまだ見つけられなかったら?原型の原型は何ですか?
原型の原型
前に、私達はもう原型も一つの対象であると言いました.対象である以上、最も原始的な方法でそれを作成することができます.
var obj = new Object();
obj.name = 'Kevin'
console.log(obj.name) // Kevin
したがって、プロトタイプのオブジェクトはObjectコンストラクタによって生成され、前述の例の_u u u uプロト.構造関数のプロトタイプを指していますので、関係図を更新します.
原型チェーン
Object.prototypeの原型は?
null、私達がプリントできるとは信じません.
console.log(Object.prototype.__proto__ === null) // true
属性を調べた時にObject.prototypeを調べたら検索を停止できます.
最後の関係図は
ちなみに、図中の相互関連のプロトタイプからなるチェーン構造はプロトタイプチェーン、つまり青いラインです.
追加
最後に、三つのポイントを追加します.みんなが気づかないところ:
トラック
まずconstructor属性です.例を見ます.
function Person() {

}
var person = new Person();
console.log(person.constructor === Person); // true
person.co nstructorを取得すると、実はpersonにはconstructor属性がなく、constructor属性が読み取れない場合、personのプロトタイプであるPerson.prototypeから読み取られます.ちょうどプロトタイプにこの属性があります.
person.constructor === Person.prototype.constructor
同前プロト.
次は_u uですproto_,ほとんどのブラウザはこの非標準的な方法のプロトタイプへのアクセスをサポートしていますが、Person.prototypeには存在しません.実際にはObject.prototypeから来ています.属性というよりは、getter/setterを使用して、Object.prototypeを使用します.プロト.を返したと理解できます.
本当に継承ですか?
最後に継承についてですが、前に述べたように、「どの対象も原型から継承されます」という属性がありますが、実際に継承は非常に迷いのある言い方です.
継承は複製操作を意味しているが、JavaScriptはデフォルトでは複製対象の属性は認められておらず、逆にJavaScriptは二つのオブジェクトの間に一つの関連を作成するだけで、一つのオブジェクトは依頼によって別のオブジェクトの属性と関数にアクセスすることができるので、継承というよりは依頼の言い方の方がより正確である.
次の文章
JavaScriptの深い語法の作用の領域と動態の作用の領域
シリーズを深く掘り下げる
JavaScriptはシリーズのディレクトリの住所に深く入ります.https://github.com/mqyqingfeng/Blog.
JavaScriptはシリーズに深く入り込んで15編ぐらい書く予定です.JavaScriptの基礎知識を整理して、プロトタイプ、作用域、実行文脈、変数オブジェクト、this、クローズド、値によって伝達、call、apply、bind、new、継承などの難点概念を重点的に解説します.
間違いや不備があったら、ぜひ指摘してください.ありがとうございます.好きだったり、何かを啓発したりすれば、starを歓迎し、作者に対しても励みになります.