ホームページ ウェブフロントエンド jsチュートリアル JavaScriptによるプロトタイプの包括的な分析

JavaScriptによるプロトタイプの包括的な分析

May 21, 2018 pm 02:53 PM
javascript js

この記事では、JavaScript におけるプロトタイプの完全な分析を主に紹介します。プロトタイプは、JS の世界における「すべてがオブジェクトである」という議論の重要なサポートであり、それを必要とする友人に役立つ情報について説明します。参考にしてください

JSのプロトタイプを理解するには、まず以下の概念を理解する必要があります
1. JSのすべてはオブジェクトです 2. JSのすべてはオブジェクトから派生します、つまり、すべてのもののプロトタイプチェーンの終点ですObject .prototype

  // ["constructor", "toString", "toLocaleString", "valueOf", "hasOwnProperty", "isPrototypeOf", 
   // "propertyIsEnumerable", "__defineGetter__", "__lookupGetter__", "__defineSetter__",
   // "__lookupSetter__"]
   console.log(Object.getOwnPropertyNames(Object.prototype));
ログイン後にコピー

を指します 3. JS におけるコンストラクターとインスタンス (オブジェクト) の微妙な関係

コンストラクターはプロトタイプを定義することでインスタンスの仕様を合意し、new を通じてインスタンスを構築するのが役割です。コンストラクター (メソッド) 自体はメソッド (関数) のインスタンスであるため、その __proto__ (プロトタイプ チェーン) も見つかります


Object / function F() {} これがコンストラクターで、1 つは JS です ネイティブ API によって提供されます1 つはカスタマイズされています
new Object() / new F() これがインスタンスです

インスタンスは、どのプロトタイプに基づいているかを知るために __proto__ を表示すること「のみ」ができます

そして、インスタンスのプロトタイプを次のように再定義することは「できません」インスタンスのインスタンスを作成します。

実践することで真の知識が得られます。自分で観察したり考えたりすることによってのみ、真に理解することができます。

prototype

プロトタイプの出力形式は次のとおりです: コンストラクター名 プロトタイプ

まず、Object.prototype の出力を見てみましょう

Object {} -> 前のオブジェクトはコンストラクターの名前です。これがプロトタイプを表す後、A {}、つまり Object オブジェクト (空のオブジェクト) のインスタンスです

次に、F {} がコンストラクターの名前であり、プロトタイプも意味するものを理解します。空のオブジェクト

  // 先来看看构造函数到底是什么
  // function Empty() {}  function Empty() {}
  console.log(Function.prototype, Function.__proto__);
  // Object {}          function Empty() {}
  console.log(Object.prototype, Object.__proto__);
  function F() {}
  // F {}              function Empty() {}
  console.log(F.prototype, F.__proto__);
ログイン後にコピー
もう少し深くして F を定義しましょう プロトタイプを使用して何が起こるか見てみましょう?
  // 再来看看由构造函数构造出来的实例
  var o = new Object(); // var o = {};
  // undefined       Object {}
  console.log(o.prototype, o.__proto__);
  function F() {}
  var i = new F();
  // undefined       F {}
  console.log(i.prototype, i.__proto__);
ログイン後にコピー

このようにすると、i が F から構築されており、プロトタイプが {a: function} であることが明確にわかります。元の空のオブジェクトのプロトタイプに新しい a メソッドがあるということです

もう一度状況を変えて、F のプロトタイプを完全にカバーしたらどうなるでしょうか

  function F() {}
  F.prototype.a = function() {};
  var i = new F();
  // undefined       F {a: function}
  console.log(i.prototype, i.__proto__);
ログイン後にコピー

どうしてですか? なぜ i が Object から構築されていることがわかりますか?

F のプロトタイプを完全にカバーしているため、実際には、プロトタイプはオブジェクト {a: function} として指定されていますが、これにより、元のコンストラクター情報が失われ、オブジェクト {a: function} で指定されたコンストラクターになります。

では、オブジェクト {a: function} のコンストラクターは何ですか?
オブジェクト {a: function} は実際には

function F() {}
  F.prototype = {
    a: function() {}
  };
  var i = new F();
  // undefined       Object {a: function}
  console.log(i.prototype, i.__proto__);
ログイン後にコピー

に相対しているため、o のコンストラクターはもちろん Object です

この間違いを修正しましょう

var o = {a: function() {}} // new了一个Object
ログイン後にコピー

正しいプロトタイプ情報を再度取得できます~

プロトタイプチェーン

では、プロトタイプチェーンとは何なのか見てみましょう

簡単に言うと、OOPの継承関係(チェーン)と同じで、レイヤーごとに上がっていきます。最終的な Object.prototype に到達するまで


最も重要なのは、JS 内のどのものが (インスタンス) オブジェクトであるかを理解することです。これは簡単です。すべてのオブジェクトにはプロトタイプがあるということです

それでは、それを証明してみましょう:2016510172352211.jpg (560×248)

  function F() {}
  F.prototype = {
    a: function() {}
  }
  // 重新指定正确的构造函数
  F.prototype.constructor = F;
  var i = new F();
  // undefined       F {a: function, constructor: function}
  console.log(i.prototype, i.__proto__);
ログイン後にコピー


プロトタイプと __proto__

すべてのオブジェクトには、このオブジェクトの「プロトタイプ」を指す __proto__ が含まれています。

同様に、すべての関数にはプロトタイプが含まれています。このプロトタイプ オブジェクトは何をするのでしょうか?

コンストラクターを使用してオブジェクトを作成する次のコードを見てみましょう (上記はリテラルの形式でオブジェクトを作成するものです)。

  Object // 这是一个函数, 函数是 Function 的实例对象, 那么就是由 Function 构造出来的
  Object.__proto__ == Function.prototype // 那么Object的原型, true
  // 这个是一个普通对象了, 因此属于 Object 的实例
  Function.prototype.__proto__ == Object.prototype // true
  // 这已经是原型链的最顶层了, 因此最终的指向 null
  Object.prototype.__proto__ == null // true

  Function // 这也是一个函数, 没错吧!
  Function.__proto__ == Function.prototype // true
  
  function A() {} // 这是一个自定义的函数, 终归还是一个函数, 没错吧! 
  A.__proto__ == Function.prototype // 任何函数都是 Function 的实例, 因此A的原型是?
  var a = new A()
  a.__proto__ == A.prototype // 实例a是由A构造函数构造出来的, 因此a的原型是由A的prototype属性定义的
  A.prototype.__proto__ == Object.prototype // 普通对象都是 Object 的示例
ログイン後にコピー
考えてみてください、この foo オブジェクトの __proto__ は何を指しているのでしょうか?

コンストラクタープロパティを含むオブジェクト?よく理解できなくても問題ありません。関数 Foo のプロトタイプ属性を出力して比較してください。

function Foo(){};
var foo = new Foo();
console.log(foo.__proto__);
ログイン後にコピー

2016510172448163.png (163×68)

新しいオブジェクト foo の __proto__ は関数 Foo のプロトタイプのみを指していることがわかります。

rreee

このような JS のデザインには何の意味があるのでしょうか?上で述べたことを思い出してください。JS の世界では、オブジェクトはクラス (モールド) に基づいて作成されるのではなく、プロトタイプ (別のオブジェクト) から派生します。

2016510172512274.png (183×69) 新しいオブジェクトを作成するために新しい操作を実行するとき、新しい操作の具体的な実装には立ち入りませんが、1 つ確かなことは、新しいオブジェクトの __proto__ がプロトタイプ オブジェクトを指しているということです。

このコードだけ

function Foo(){};
var foo = new Foo();
ログイン後にコピー

foo.__proto__到底要指向谁了?你怎么不能指向Foo这个函数本身吧,虽然函数也是对象,这个有机会会详细讲。但如何foo.__proto__指向Foo固然不合适,因为Foo是一个函数,有很多逻辑代码,foo作为一个对象,继承逻辑处理没有任何意义,它要继承的是“原型对象”的属性。

所以,每个函数会自动生成一个prototype对象,由这个函数new出来的对象的__proto__就指向这个函数的prototype。

foo.__proto__ --> Foo.prototype
ログイン後にコピー

总结说了这么多,感觉还是没完全说清楚,不如上一张图。我曾经参考过其他网友的图,但总觉得哪里没说清楚,所以我自己画了一张图,如果觉得我的不错,请点个赞!(老子可是费了牛劲才画出来)。

2016510172555695.png (800×600)

咱们就着这张图,记住如下几个事实:

1. 每个对象中都有一个_proto_属性。

JS世界中没有类(模具)的概念,对象是从另一个对象(原型)衍生出来的,所以每个对象中会有一个_proto_属性指向它的原型对象。(参考左上角的那个用字面量形式定义的对象obj,它在内存中开辟了一个空间存放对象自身的属性,同时生成一个_proto_指向它的原型——顶层原型对象。)

2. 每个函数都有一个prototype属性。

“构造函数”为何叫构造函数,因为它要构造对象。那么根据上面第一条事实,构造出来的新对象的_proto_属性指向谁了?总不能指向构造函数自身,虽然它也是个对象,但你不希望新对象继承函数的属性与方法吧。所以,在每个构造函数都会有一个prototype属性,指向一个对象作为这个构造函数构造出来的新对象的原型。

3. 函数也是对象。

每个函数都有一些通用的属性和方法,比如apply()/call()等。但这些通用的方法是如何继承的呢?函数又是怎么创建出来的呢?试想想,一切皆对象,包括函数也是对象,而且是通过构造函数构造出来的对象。那么根据上面第二条事实,每个函数也会有_proto_指向它的构造函数的prototype。而这个构造函数的函数就是Function,JS中的所有函数都是由Function构造出来的。函数的通用属性与方法就存放在Function.prototype这个原型对象上。

上面是我整理给大家的,希望今后会对大家有帮助。

相关文章:

全面分析JavaScript面向对象概念中的Object类型与作用域(附有示例)

在javascript中创建对象的各种模式解析(图文教程)

详细解读JavaScript设计模式开发中的桥接模式(高级篇)

以上がJavaScriptによるプロトタイプの包括的な分析の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。

ホットAIツール

Undresser.AI Undress

Undresser.AI Undress

リアルなヌード写真を作成する AI 搭載アプリ

AI Clothes Remover

AI Clothes Remover

写真から衣服を削除するオンライン AI ツール。

Undress AI Tool

Undress AI Tool

脱衣画像を無料で

Clothoff.io

Clothoff.io

AI衣類リムーバー

AI Hentai Generator

AI Hentai Generator

AIヘンタイを無料で生成します。

ホットツール

メモ帳++7.3.1

メモ帳++7.3.1

使いやすく無料のコードエディター

SublimeText3 中国語版

SublimeText3 中国語版

中国語版、とても使いやすい

ゼンドスタジオ 13.0.1

ゼンドスタジオ 13.0.1

強力な PHP 統合開発環境

ドリームウィーバー CS6

ドリームウィーバー CS6

ビジュアル Web 開発ツール

SublimeText3 Mac版

SublimeText3 Mac版

神レベルのコード編集ソフト(SublimeText3)

WebSocket と JavaScript を使用してオンライン音声認識システムを実装する方法 WebSocket と JavaScript を使用してオンライン音声認識システムを実装する方法 Dec 17, 2023 pm 02:54 PM

WebSocket と JavaScript を使用してオンライン音声認識システムを実装する方法 はじめに: 技術の継続的な発展により、音声認識技術は人工知能の分野の重要な部分になりました。 WebSocket と JavaScript をベースとしたオンライン音声認識システムは、低遅延、リアルタイム、クロスプラットフォームという特徴があり、広く使用されるソリューションとなっています。この記事では、WebSocket と JavaScript を使用してオンライン音声認識システムを実装する方法を紹介します。

推奨: 優れた JS オープンソースの顔検出および認識プロジェクト 推奨: 優れた JS オープンソースの顔検出および認識プロジェクト Apr 03, 2024 am 11:55 AM

顔の検出および認識テクノロジーは、すでに比較的成熟しており、広く使用されているテクノロジーです。現在、最も広く使用されているインターネット アプリケーション言語は JS ですが、Web フロントエンドでの顔検出と認識の実装には、バックエンドの顔認識と比較して利点と欠点があります。利点としては、ネットワーク インタラクションの削減とリアルタイム認識により、ユーザーの待ち時間が大幅に短縮され、ユーザー エクスペリエンスが向上することが挙げられます。欠点としては、モデル サイズによって制限されるため、精度も制限されることが挙げられます。 js を使用して Web 上に顔検出を実装するにはどうすればよいですか? Web 上で顔認識を実装するには、JavaScript、HTML、CSS、WebRTC など、関連するプログラミング言語とテクノロジに精通している必要があります。同時に、関連するコンピューター ビジョンと人工知能テクノロジーを習得する必要もあります。 Web 側の設計により、次の点に注意してください。

株価分析に必須のツール: PHP と JS を使用してローソク足チャートを描画する手順を学びます 株価分析に必須のツール: PHP と JS を使用してローソク足チャートを描画する手順を学びます Dec 17, 2023 pm 06:55 PM

株式分析に必須のツール: PHP および JS でローソク足チャートを描画する手順を学びます。特定のコード例が必要です。インターネットとテクノロジーの急速な発展に伴い、株式取引は多くの投資家にとって重要な方法の 1 つになりました。株価分析は投資家の意思決定の重要な部分であり、ローソク足チャートはテクニカル分析で広く使用されています。 PHP と JS を使用してローソク足チャートを描画する方法を学ぶと、投資家がより適切な意思決定を行うのに役立つ、より直感的な情報が得られます。ローソク足チャートとは、株価をローソク足の形で表示するテクニカルチャートです。株価を示しています

WebSocket と JavaScript: リアルタイム監視システムを実装するための主要テクノロジー WebSocket と JavaScript: リアルタイム監視システムを実装するための主要テクノロジー Dec 17, 2023 pm 05:30 PM

WebSocketとJavaScript:リアルタイム監視システムを実現するためのキーテクノロジー はじめに: インターネット技術の急速な発展に伴い、リアルタイム監視システムは様々な分野で広く利用されています。リアルタイム監視を実現するための重要なテクノロジーの 1 つは、WebSocket と JavaScript の組み合わせです。この記事では、リアルタイム監視システムにおける WebSocket と JavaScript のアプリケーションを紹介し、コード例を示し、その実装原理を詳しく説明します。 1.WebSocketテクノロジー

JavaScript と WebSocket を使用してリアルタイムのオンライン注文システムを実装する方法 JavaScript と WebSocket を使用してリアルタイムのオンライン注文システムを実装する方法 Dec 17, 2023 pm 12:09 PM

JavaScript と WebSocket を使用してリアルタイム オンライン注文システムを実装する方法の紹介: インターネットの普及とテクノロジーの進歩に伴い、ますます多くのレストランがオンライン注文サービスを提供し始めています。リアルタイムのオンライン注文システムを実装するには、JavaScript と WebSocket テクノロジを使用できます。 WebSocket は、TCP プロトコルをベースとした全二重通信プロトコルで、クライアントとサーバー間のリアルタイム双方向通信を実現します。リアルタイムオンラインオーダーシステムにおいて、ユーザーが料理を選択して注文するとき

WebSocketとJavaScriptを使ったオンライン予約システムの実装方法 WebSocketとJavaScriptを使ったオンライン予約システムの実装方法 Dec 17, 2023 am 09:39 AM

WebSocket と JavaScript を使用してオンライン予約システムを実装する方法 今日のデジタル時代では、ますます多くの企業やサービスがオンライン予約機能を提供する必要があります。効率的かつリアルタイムのオンライン予約システムを実装することが重要です。この記事では、WebSocket と JavaScript を使用してオンライン予約システムを実装する方法と、具体的なコード例を紹介します。 1. WebSocket とは何ですか? WebSocket は、単一の TCP 接続における全二重方式です。

PHP および JS 開発のヒント: 株価ローソク足チャートの描画方法をマスターする PHP および JS 開発のヒント: 株価ローソク足チャートの描画方法をマスターする Dec 18, 2023 pm 03:39 PM

インターネット金融の急速な発展に伴い、株式投資を選択する人がますます増えています。株式取引では、ローソク足チャートは一般的に使用されるテクニカル分析手法であり、株価の変化傾向を示し、投資家がより正確な意思決定を行うのに役立ちます。この記事では、PHP と JS の開発スキルを紹介し、株価ローソク足チャートの描画方法を読者に理解してもらい、具体的なコード例を示します。 1. 株のローソク足チャートを理解する 株のローソク足チャートの描き方を紹介する前に、まずローソク足チャートとは何かを理解する必要があります。ローソク足チャートは日本人が開発した

JavaScript と WebSocket: 効率的なリアルタイム天気予報システムの構築 JavaScript と WebSocket: 効率的なリアルタイム天気予報システムの構築 Dec 17, 2023 pm 05:13 PM

JavaScript と WebSocket: 効率的なリアルタイム天気予報システムの構築 はじめに: 今日、天気予報の精度は日常生活と意思決定にとって非常に重要です。テクノロジーの発展に伴い、リアルタイムで気象データを取得することで、より正確で信頼性の高い天気予報を提供できるようになりました。この記事では、JavaScript と WebSocket テクノロジを使用して効率的なリアルタイム天気予報システムを構築する方法を学びます。この記事では、具体的なコード例を通じて実装プロセスを説明します。私たちは

See all articles