継承は、ほとんどの話概念のオブジェクト指向言語です。インターフェイスの継承と実装の継承:多くのオブジェクト指向言語は、継承の2種類をサポートしています。インタフェースの継承は、メソッドシグネチャを継承し、実際のメソッドの実装継承は継承されています。
---この記事の抜粋「JavaScriptの高度なプログラミング(第3版)」
機能が署名されていないので、ECMAScriptのインタフェースの継承で達成することができません。ECMAScirptは、実装の継承をサポートし、実装の継承は、主に達成するために、そのプロトタイプチェーンに依存します。
プロトタイプチェーン
ECMAScriptのプロトタイプ実装方法の継承の主鎖として記載されています。
基本的な考え方:参照型は参照プロパティとメソッドの別のタイプから継承するためにプロトタイプを使用しています。
PSは:各コンストラクタがプロトタイプオブジェクトを持って、プロトタイプオブジェクトはコンストラクタを指すポインタが含まれ、その例はすべて、プロトタイプオブジェクトへのポインタが含まれています。
これプロトタイプオブジェクトインスタンスはプロトタイプオブジェクトは、別のプロトタイプを指すポインタを含む場合には、別のタイプ、と等しい場合に、プロトタイプはまた、別のコンストラクタを指す他のポインタを含みます。別の例では、別の種類のプロトタイプが、そのようなプログレッシブ層は鎖および試作例を形成することです。
JS code:
function SuperType(){
this.property = true;
};
SuperType.prototype.getSuperValue = function(){
return this.property;
};
function SubType(){
this.subproperty = false;
}
// 继承了SuperType
SubType.prototype = new SuperType();
SubType.prototype.getSubValue = function(){
return this.subproperty;
};
var instance = new SubType();
alert(instance.getSuperValue()); // true
复制代码
:コードの上に2種類の定義スーパータイプとサブタイプを。各属性は、それぞれの種類や方法があります。主な違いは、サブタイプがスーパータイプを継承し、継承インスタンススーパータイプを作成することであり、そのインスタンスSubType.prototype実装を割り当てることです。本質プロトタイプオブジェクトインプリメンテーションは、タイプの新しいインスタンスで置き換え、書き換えられます。
注:instance.constructorは今、元SubType.prototypeは、コンストラクタのために書き換えることがあるため、これは、スーパータイプを指しています。
不十分:プロトタイプによる継承を実装する際に、プロトタイプは、実際には別のタイプの例になります。したがって、元のインスタンスのプロパティは当然現在のプロトタイプのプロパティになるであろう。次のコードは、問題を説明することができます。
JS code:
function SuperType(){
this.colors = ["red", "blue", "green"];
}
function SubType(){
}
SubType.prototype = new SuperType(); //继承了 SuperType
var instance1 = new SubType();
instance1.colors.push("black");
alert(instance1.colors); //"red,blue,green,black"
var instance2 = new SubType();
alert(instance2.colors); //"red,blue,green,black"
复制代码
PS:スーパーコンストラクタのタイプにパラメータを渡すことができないサブタイプのインスタンスを作成する場合、この欠点は、プロトタイプチェーンを継承しています。
借入コンストラクタ[偽のオブジェクトや古典の継承]
基本的な考え方:サブタイプのコンストラクタ内では、スーパータイプのコンストラクタを呼び出します。関数は、ちょうどそう適用されます()と()メソッドの呼び出しも(将来的に)オブジェクトのコンストラクタで実行することができ、新しく作成されたを使用することにより、特定の環境でコードを実行するオブジェクトです。
JS code:
function SuperType(){
this.colors = ["red", "blue", "green"];
}
function SubType(){
//继承了 SuperType
SuperType.call(this);
}
var instance1 = new SubType();
instance1.colors.push("black");
alert(instance1.colors); //"red,blue,green,black"
var instance2 = new SubType();
alert(instance2.colors); //"red,blue,green"
复制代码
ことによって、上記のコード[()メソッドを適用しますか]の呼び出し()メソッドを使用しては、我々は実際に新しく作成されたサブタイプインスタンス環境でのスーパータイプのコンストラクタと呼ばれます。これは、新しいサブタイプオブジェクト内の初期化コードで定義されたすべてのオブジェクトスーパータイプ()関数を実行します。その結果、各インスタンスは、市内での色のサブタイプ属性の独自のコピーを持っています。
PS:相対プロトタイプチェーン、借りコンストラクタはここには示されていない、コンストラクタのスーパータイプサブタイプのコンストラクタに引数を渡すことができます大きな利点を持っている、ちょうど()(呼び出すメソッド[または適用されます)方法]特性。
不十分:メソッドは、コンストラクタで定義され、その機能は論外で再利用されています。また、サブタイプに対して、スーパータイプのプロトタイプで定義されたメソッドが表示されていない、すべての種類の結果は、コンストラクタのモードを使用することができます。
継承の組み合わせ[擬似古典的な遺伝]
基本的な考え方:継承モードの長いものを再生どちらのコンストラクタに借り組成とプロトタイプチェーン技術、。プロトタイプ実装継承チェーンのプロパティとメソッドのプロトタイプを使用して、そして借りコンストラクタによって継承インスタンス属性を達成することの背後にある考え方。
JS code:
function SuperType(name){
this.name = name;
this.colors = ["red", "blue", "green"];
}
SuperType.prototype.sayName = function(){
alert(this.name);
};
function SubType(name, age){
//继承属性
SuperType.call(this, name);
this.age = age;
};
//继承方法
SubType.prototype = new SuperType();
SubType.prototype.constructor = SubType;
SubType.prototype.sayAge = function(){
alert(this.age);
};
var instance1 = new SubType("Nicholas", 29);
instance1.colors.push("black");
alert(instance1.colors); //"red,blue,green,black"
instance1.sayName(); //"Nicholas";
instance1.sayAge(); //29
var instance2 = new SubType("Greg", 27);
alert(instance2.colors); //"red,blue,green"
instance2.sayName(); //"Greg";
instance2.sayAge(); //27
复制代码
名前と色:スーパータイプのコンストラクタは二つの属性を定義します。スーパープロトタイプは方法sayName()を定義します。別続くスーパーコンストラクタを呼び出すときに、nameパラメータに渡されたサブタイプコンストラクタは、独自のプロパティの年齢を定義します。例としては、スーパータイプ)(次いでサブタイプは、プロトタイプに割り当てられ、その後、新しいプロトタイプ方法sayAgeを定義します。彼らは同じメソッドを使用することができ、色のプロパティを含む - この方法では、あなたは、2つの異なるインスタンスが、両方が自分の財産を所有していたサブタイプにすることができます。
継承と回避借入コンストラクタのプロトタイプチェーンの欠陥の組み合わせは、その利点を組み合わせ、JavaScriptは継承の最も一般的に使用されるモードになっています。さらに、のinstanceofとisPrototypeOf()はまた、複合遺伝に基づいて作成されたオブジェクトを識別するために使用することができます。
原型継承
基本的な考え方は:プロトタイプを使用すると、既存のオブジェクトに基づいて新しいオブジェクトを作成することができ、またそのためのカスタムタイプを作成する必要はありません。以下の機能を参照してください。
JS code:
function object(o){
function F(){};
F.prototype = o;
return new F();
}
复制代码
内部オブジェクト()関数では、第1の一時コンストラクタを作成し、プロトタイプコンストラクタとしてオブジェクトを渡し、この一時的なタイプの新しいインスタンスを返します。本質的に、オブジェクトは、()は、着信オブジェクト実行する浅いコピーを。
PS:請求継承におけるプロトタイプ式が別のオブジェクトのオブジェクトの基礎としてでなければなりません。そのようなオブジェクトが存在する場合、それは、オブジェクト()関数に渡すことができ、その後、オブジェクトの特定のニーズを取得変更されます。
ECMAScriptの5 新しいObject.create()メソッドによって標準化された原型継承。
この方法は、2つのパラメータを取ります
- 新しいオブジェクトのプロトタイプオブジェクトとして、及び(オプション)
- カスタムは、新しいオブジェクトの追加のプロパティをオブジェクト。
JS code:
var person = {
name: "Nicholas",
friends: ["Shelby", "Court", "Van"]
};
var anotherPerson = Object.create(person);
anotherPerson.name = "Greg";
anotherPerson.friends.push("Rob");
var yetAnotherPerson = Object.create(person);
yetAnotherPerson.name = "Linda";
yetAnotherPerson.friends.push("Barbie");
alert(person.friends); //"Shelby,Court,Van,Rob,Barbie"
复制代码
PS:第2の位相フォーマットパラメータの2番目のパラメータObject.defineProperties Object.create()メソッド()メソッド
同じ、ここでは説明なし。
該当シーンは:ちょうど似たような状況下に置か別のオブジェクトに1つのオブジェクトを作りたい、プロトタイプ・スタイルの継承は完全に可能である、しかし、プロパティの型への参照が常に同じプロトタイプのモードを使用して、対応する値の値を共有しますが含まれています。
寄生継承
基本的な考え方:オブジェクトを強化するためにいくつかの方法で内部的に、機能のみを承継するプロセスをカプセル化するために使用される関数を作成するために、そして最終的に本当にすべての作業だけで返されたオブジェクトをしたいです。
JS code:
function createAnother(original){
var clone = object(original); //通过调用函数创建一个新对象
clone.sayHi = function(){ //以某种方式来增强这个对象
alert("hi");
};
return clone; //返回这个对象
}
var person = {
name: "Nicholas",
friends: ["Shelby", "Court", "Van"]
};
var anotherPerson = createAnother(person);
anotherPerson.sayHi(); //"hi"
复制代码
ベースの人は[anotherPerson]新しいオブジェクトを返す。のみ新しいオブジェクトは、人のすべてのプロパティとメソッドを有するだけでなく、独自のsayHi()メソッドを持っていません。
該当するシーン:主な考慮事項ではなく定義されたタイプとコンストラクタの場合と比べてオブジェクト寄生継承が有用なモデルです。
組み合わせ寄生継承
ここ組み合わせ継承が来る説明:問題 1は、サブタイプのプロトタイプの作成であり、かつ一度のサブタイプのコンストラクタの内部:どのような状況の下で、二回タイプのコンストラクタを介して呼び出されるに関係なく。 サブタイプは、最終的にスーパータイプのオブジェクトのすべてのインスタンスのプロパティが含まれますが、我々は、サブタイプのコンストラクタを呼び出すときに、これらの属性を書き換える必要があります。
以下は、複合遺産です。
JS code:
function SuperType(name){
this.name = name;
this.colors = ["red", "blue", "green"];
}
SuperType.prototype.sayName = function(){
alert(this.name);
};
function SubType(name, age){
SuperType.call(this, name); // 第二次调用SuperType()
this.age = age;
}
SubType.prototype = new SuperType(); // 第一次调用SuperType()
SubType.prototype.constructor = SubType;
SubType.prototype.sayAge = function(){
alert(this.age);
};
复制代码
最初のコールのスーパータイプのコンストラクタ、SubType.prototypeは二つの属性を取得します:名前と色を、彼らはスーパータイプのインスタンスプロパティですが、今のサブタイプのプロトタイプを設置します。
サブタイプコンストラクタを呼び出すときになる二コール・スーパーコンストラクタ、今度は新しいオブジェクトのプロパティ名と色のインスタンスを作成します
したがって、2つのプロトタイプの性質をシールド上に同じ名前を持つこれら二つの属性。
[継承寄生モジュラー]基本的な考え方は:借入コンストラクタによってプロパティを継承するために、方法は、ブレンドフォームプロトタイプチェーンを継承します。
JS code:function inheritPrototype(subType, superType){
var prototype = object(superType.prototype); // 创建对象
prototype.constructor = subType; // 增强对象
subType.prototype = prototype; // 指定对象
}
复制代码
サブタイプおよびスーパータイプコンストラクタコンストラクタ:この関数は2つの引数を受け入れます。
関数内、最初のステップは、スーパータイプのプロトタイプのコピーを作成することです。
第二段階は、デフォルトコンストラクタのプロパティを書き換えるので、コピーコンストラクタのプロパティが作成された追加プロトタイプの損失を補償することです。
最終ステップ、新たに作成されたサブタイプのプロトタイプに割り当てられたオブジェクト(すなわち、コピー)。
このように、我々は、前の例では文を置き換えるためにinheritPrototype()文関数を呼び出す使用できる割り当てのプロトタイプのサブタイプです。
JS code:
function SuperType(name){
this.name = name;
this.colors = ["red", "blue", "green"];
}
SuperType.prototype.sayName = function(){
alert(this.name);
};
function SubType(name, age){
SuperType.call(this, name);
this.age = age;
}
inheritPrototype(SubType, SuperType);
SubType.prototype.sayAge = function(){
alert(this.age);
};
复制代码
PS:寄生継承高い効率のみスーパーコンストラクタ一度呼び出さ組み合わせに反映され、そしてプロトタイプチェーンは変化しないままであり得るしつつ、特性の上サブタイプのプロトタイプに不要な過剰の生成を回避;.
だから、開発者は、一般的に結合し、寄生継承は理想的な参照型はパラダイムを継承していると信じています。
ESMA5の継承は、以下のチャートで要約することができます。
まあ、それはフロントHunzi継承を省略クラスECMA6は、大きな神で満たされたメッセージを残すことを歓迎継承ECMA5、の6種類を知っているのです。
最後に、私はあなたにすべての幸せな週末をしたいです!
ます。https://juejin.im/post/5d006e2de51d45105d63a4ebで再現