JavaScript の継承についてどれくらい知っていますか?

JavaScript の継承についてどれくらい知っていますか?

序文

継承についてどれくらい知っていますか?どのような継承が最適でしょうか?継承に関するいくつかの知識ポイントを学び、その実装プロセスと利点と欠点を紹介します。

コンストラクタ、プロトタイプオブジェクト、インスタンスオブジェクトの関係

まずそれらの関係を理解することで、継承をよりよく理解できるようになります

プロトタイプチェーン継承

コア: 親クラスのインスタンスをサブクラスのプロトタイプとして使用する

コード実装プロセス:

関数 Parent(名前){
    this.name = 名前 || 'xt',
    this.arr = [1]
}
関数Son(年齢){
    this.age = 年齢
}
Parent.prototype.say = function() { //親クラスのプロトタイプで再利用および共有する必要があるメソッドを定義します。console.log('hello');
}
Son.prototype = 新しい親()
s1 = 新しいSon(18)とする
s2 = new Son(19)とする
console.log(s1.say() === s2.say()); //true
console.log(s1.name,s1.age); //xt 18
console.log(s2.name,s2.age); //xt 19
s1.arr.push(2)
console.log(s1.arr,s2.arr); // [ 1, 2 ] [ 1, 2 ]

アドバンテージ:

インスタンスが継承できる属性は、インスタンスのコンストラクターの属性、親クラスのコンストラクターの属性、および親クラスのプロトタイプの属性です。 (新しいインスタンスは親クラス インスタンスのプロパティを継承しません!)

欠点:

  • サブクラスのインスタンスは、arr プロパティなどの親クラスのコンストラクターの参照プロパティを共有します (プロトタイプのプロパティは共有され、1 つのインスタンスがプロトタイプ プロパティを変更すると、他のインスタンスのプロトタイプ プロパティも変更されます)。
  • 親クラスのコンストラクタにパラメータを渡すことができません

コンストラクタ継承の借用

コア: 親クラスのコンストラクターを使用して子クラスのインスタンスを拡張します。これは、親クラスのインスタンス属性を子クラスにコピーすることと同じです。

コード実装:

関数 親(名前) {
    this.name = 名前;
    this.arr = [1],
    this.say = function() { console.log('hello') }
}
関数 Son(名前, 年齢) {
    Parent.call(this, name) //親クラスのインスタンスプロパティとメソッドをコピーします this.age = age
}
s1 = new Son('小谭', 18) とします。
s2 = new Son('Xiaoming', 19) とします。
console.log(s1.say === s2.say) //false メソッドは再利用できません。メソッドは独立しており、共有されていません。 console.log(s1.name, s1.age); //Xiao Tan 18
console.log(s2.name, s2.age); //Xiaoming19
s1.arr.push(2)
console.log(s1.arr, s2.arr); // [ 1, 2 ] [ 1 ]

アドバンテージ:

  • 親クラス コンストラクターのプロパティのみを継承し、親クラス プロトタイプのプロパティは継承しません。
  • 複数のコンストラクタプロパティを継承できる(複数呼び出し)
  • 子インスタンスでは、パラメータを親インスタンスに渡すことができます。

欠点:

  • 親クラスのコンストラクターからのみプロパティを継承できます。
  • コンストラクタの再利用はできません。 (使用するたびに再度呼び出す必要があります)
  • それぞれの新しいインスタンスには、肥大化した親クラスのコンストラクターのコピーが含まれます。

プロトタイプ継承

コア: オブジェクトを関数でラップし、この関数の呼び出しを返します。この関数は、任意に属性を追加できるインスタンスまたはオブジェクトになります。

関数 親(名前) {
    this.name = 'xt';
    this.arr = [1]
}
関数オブジェクト(obj){
    関数 F(){}
    F.プロトタイプ = obj;
    新しいF()を返します。
  }
s1 = 新しい親(オブジェクト)
s1.name = 'シャオミン'
s1.arr.push(2)
s2 = 新しい親(オブジェクト)
console.log(s1.name,s2.name); // Xiaoming xt
console.log(s1.arr, s2.arr); //[ 1, 2 ] [ 1 ]

欠点:

  • すべてのインスタンスはプロトタイプのプロパティを継承し、パラメータを渡すことはできません。
  • 再利用はできません。 (新しいインスタンス属性は後で追加されます)

寄生遺伝

コア: プロトタイプ継承に基づいてオブジェクトを拡張し、コンストラクタを返す

関数 親(名前) {
    this.name = 'xt';
    this.arr = [1]
}
関数オブジェクト(obj){
    関数 F(){}
    F.プロトタイプ = obj;
    新しいF()を返します。
  }
息子 = 新しい親()
関数addobject(obj){
    var add = オブジェクト(obj)
    add.name = 'シャオバイ'
    戻る追加
}
var s1 = addobject(息子)
console.log(s1.name); //小白

欠点:

  • プロトタイプは使用されず、再利用できません。
  • プロトタイプ チェーンによって継承された複数のインスタンスの参照型プロパティは同じものを指すため、改ざんが発生する可能性があります。

結合継承(プロトタイプチェーン継承と借用コンストラクタ継承の組み合わせ)

コア: 親クラスのコンストラクターを呼び出すことで、親クラスのプロパティが継承され、パラメーター渡しの利点が保持されます。次に、親クラスのインスタンスをサブクラスのプロトタイプとして使用することで、関数の再利用が実現されます。

コード実装:

関数 親(名前) {
    this.name = 名前;
    this.arr = [1]
}
Parent.prototype.say = function () { console.log('hello') }
関数 Son(名前, 年齢) {
    Parent.call(this, name) // 2回目 this.age = age
}
Parent.prototype = new Son() // 一度、let s1 = new Son('小谭', 18)
s2 = new Son('Xiaoming', 19) とします。
console.log(s1.say === s2.say) // 真
console.log(s1.name, s1.age); //シャオタン18
console.log(s2.name, s2.age); //Xiaoming19
s1.arr.push(2)
console.log(s1.arr, s2.arr); // [ 1, 2 ] [ 1 ] は親クラスの参照プロパティを共有しません。

アドバンテージ:

  • コンストラクターを保持する利点: サブクラスのインスタンスを作成するときに、親クラスのコンストラクターにパラメーターを渡すことができます。
  • プロトタイプ チェーンを保持する利点: 親クラスのメソッドは親クラスのプロトタイプ オブジェクト上で定義されるため、メソッドの再利用を実現できます。
  • 親クラスの参照プロパティは共有されません。例えば、arr属性

欠点:

  • 親クラスのコンストラクターが 2 回呼び出されるため、冗長な親クラスのインスタンス属性が存在することになります。

寄生的組み合わせ継承

コア: パラメータを渡すための借用コンストラクタと継承を実現するための寄生パターンを組み合わせる

関数 Parent(名前){
    this.name = 名前 || 'xt',
    this.arr = [1]
}
関数 Son(名前,年齢){
    Parent.call(this,name) // コア
    this.age = 年齢
}
Parent.prototype.say = function() {  
    コンソールにログ出力します。
}
Son.prototype = Object.create(Parent.prototype) // コアは中間オブジェクトを作成し、子クラスのプロトタイプと親クラスのプロトタイプは分離されます。
Son.prototype.constructor = Son
p1 = 新しい親()

s1 = new Son("Xiaohong",18) とします。
s2 = new Son("小黒",19) とします。
console.log(p1.constructor); //[関数: 親]
console.log(s1.constructor); // [関数: Son]
console.log(s1.say() === s2.say()); //true
console.log(s1.name,s1.age); // シャオホン 18
console.log(s2.name,s2.age); //リトルブラック19
s1.arr.push(2)
console.log(s1.arr,s2.arr); // [ 1, 2 ] [ 1, 2 ]

寄生的合成継承は参照型継承の最良の継承とみなすことができる

要約する

JS継承に関する記事はこれで終了です。JS継承についてさらに詳しく知りたい方は、123WORDPRESS.COMの過去の記事を検索するか、以下の関連記事を引き続きご覧ください。今後とも123WORDPRESS.COMをよろしくお願いいたします。

以下もご興味があるかもしれません:
  • Js クラスの構築と継承のケースの詳細な説明
  • JS関数の継承について学ぶ記事
  • JS における ES6 継承と ES5 継承の違い
  • JavaScript の寄生的構成継承についての簡単な説明
  • JavaScript オブジェクト指向クラス継承ケースの説明
  • JavaScript継承のさまざまな方法とメリット・デメリットを詳しく解説

<<:  MYSQL パフォーマンス アナライザー EXPLAIN 使用例分析

>>:  Nexusプライベートサーバー構築原理とチュートリアル分析

推薦する

htmlはハイパーリンク付きの新しいウィンドウを開き、ウィンドウのプロパティを制御できます。

1. HTMLハイパーリンクによって開かれるウィンドウのサイズコードをコピーコードは次のとおりです...

docker を使用して influxdb と mongo をデプロイするための一般的なコマンド

Docker ベースのデータベースをデプロイするsudo docker pull influxdb ...

HTMLはa要素hrefのURLリンクを自動的に更新したり新しいウィンドウを開いたりする機能を実装する

場合によっては、次のような機能を実装したいことがあります。リンクをクリックします。リンクがブラウザで...

Ubuntu 19.04 インストール チュートリアル (画像とテキストの手順)

1. 準備1.1 VMware 15 をダウンロードしてインストールするダウンロード リンク: h...

MySQL 面接でよく聞かれる質問への回答

序文:さまざまな技術職の面接では、MySQL 関連の質問がよくされるようです。開発職の面接でも運用職...

Centos7にGitLabサーバーをインストールして展開する方法

私はここでCentOS 7 64ビットシステムを使用しています。CentOS 64ビットシステムを試...

Vue で $attrs と $listeners を使用するチュートリアル

目次導入例要約する導入$属性すべての親コンポーネントのプロパティを継承します (props を通じて...

Vue を使用して Web ページのスクリーンショットを撮る方法をご存知ですか?

目次1. html2Canvasをインストールする2. 必要なVueコンポーネントを導入する3. ス...

Vueフォームで画像を処理する方法

質問: Vue にブログ投稿をアップロードするためのフォームがあり、タイトル、本文、説明、スニペット...

Vue のスロットとフィルターの詳細な説明

目次スロットスロットとは何ですか?スロットの内容コンパイルスコープフォールバックコンテンツ名前付きス...

LinuxのCPU負荷とCPU使用率の詳細な説明

CPU 負荷と CPU 使用率これらは両方とも、ある程度、マシンの忙しさを反映できます。 CPU 使...

ログインフォームを実装するためのReactサンプルコード

Vue ユーザーとして、React を拡張する時が来ました。antd の導入、less と rout...

MySQLでSQL文がどのように実行されるかの詳細な説明

概要最近MySQL関連の知識を勉強し始めました。学んだ知識ポイントと自分の理解を元に整理して共有しま...

Vueフレームワークで習得しなければならない重要な知識を学びます

1. Vueとは何かVue は、ユーザー ページを構築するためのプログレッシブ フレームワークです。...

CentOS7 に Redis をインストールして設定する方法

導入Redis を詳しく説明する必要はありません。インストールと設定を始めましょう。インストールソー...