2016-04-10 11 views
2

I持っている疑問、多分少し珍しい、関数のプロトタイプについては、このコードを見ると、コンソール出力表すコメント注意:理解関数プロトタイプと__proto__

function Foo() { 
 
}; 
 

 
var o = Foo.prototype; 
 

 
console.log(o.__proto__); // Object {} 
 
console.log(o.constructor); // function Foo() {} 
 
console.log(o.__proto__.constructor); // function Object() { [native code] } 
 

 
console.log(o.__proto__.constructor === o.constructor); // false

をしてください私が標準getPrototypeOf()の代わりに__proto__を使用していることを無視してください。

最後の行がfalseを印刷する理由を理解しようとしています。私たちは、通常、任意のは、以下の目的のために真実であることを知っている:

obj.__proto__.constructor === obj.constructor

が、これはoがあまりにもオブジェクトであるとして、上記oの場合ではない理由を理解するために楽しみにしています。

oが実際に関数のプロトタイプのインスタンス(Foo.prototype)であるため、それはFooセットアップ中Fooo.constructorセットを取得しますので、それは偽だのだろうか。

これはあまり実用的ではないかもしれないが、いくつかのことを理解することは有益です。

+0

"*いつもどんなオブジェクトでも、以下のことが当てはまります:' obj .__ proto __。constructor === obj.constructor' * " - 独自の' .constructor'プロパティを持たないオブジェクト。 'Foo.prototype' *には' Foo'を指し示す独自の 'constructor'プロパティがあります。 – Bergi

+0

@Bergiどのオブジェクトも 'constructor'プロパティを持っていると思います。 'constructor'プロパティを持つ' Object.prototype'から継承しています。あなたが何を意味しているか分かりませんが、ちょっとした詳細を喜ばせることができれば、それは役に立つでしょう、ありがとう。 –

+0

私は自分のプロパティを、継承されたものは意味しませんでした。また、 'Object.prototype'を継承しないオブジェクトを作成することもできます。つまり、Object.create(null)の' "constructor"はfalseです) – Bergi

答えて

3

これは不変ではありません。

Object.getPrototypeOf(obj).constructor === obj.constructor 

代わりに、それだけでは通常、人々は彼らのオブジェクトにカスタムconstructorプロパティを追加していないだし、ほとんどのオブジェクトは、コンストラクタのprototypeオブジェクトではありません。したがって、constructorプロパティにアクセスすると、[[Prototype]](存在する場合)から継承した値が取得されます。

function Foo(){} 
Foo.prototype.constructor; // Foo (own property) 
new Foo().constructor; // Foo (inherited from Foo.prototype) 

しかし、コンストラクタのprototypeオブジェクトは、[[プロトタイプ]](もしあれば)のconstructorよりも、通常は異なり、デフォルトで独自のconstructor性質を持っています。

function Foo(){} 
Foo.prototype.constructor; // Foo (own property) 
var proto = Object.getPrototypeOf(Foo.prototype); // Object.prototype 
proto.constructor; // Object (own property of proto/Object.prototype) 

constructorについての特別なものは何もありません忘れないでください、それはあなたがインスタンスからのコンストラクタを得るのを助けるために、コンストラクタのprototypeオブジェクトに自動的に作成されただけで、通常のプロパティです。しかし、それを修正、削除、またはシャドーすることができます。

+0

's /しかし、コンストラクタ/プロトタイプ/' iiuc – Siguza

+0

@Oriol:ありがとう。 'Foo.prototype.constructor'が' Object.getPrototypeOf(Foo.prototype).constructor'と違うと言うのは正しいでしょうか? 'Foo.prototype'が作られたとき、JSエンジンは' Foo.prototype 'のようなことをしたからです。コンストラクタ= Foo'となり、このようにして継承した 'constructor'プロパティ値を' Object.prototype.constructor'から「変更」しましたか? –

+0

JSエンジンの実際のC++コードに基づいて、誰かがブログや書いてどこかに書いて、 'prototype'と' constructor'が 'Function'と' Object'のためにどのように設定されているかを知りたいと思っています。これらのことがJSでどのように機能するかについての混乱について、いくつかの光を当てるでしょう –

関連する問題