Lately I'm trying to get the technical aspects of the prototype chain. Now I have a few questions about object instantiation.
Consider the following code:
var Foo = function(s) {
this._bar = s;
};
var fooInst = new Foo('test');
Now when I examine the created object, then:
Foo.prototype === Function.prototype; // true
fooInst.prototype === ?
fooInst.prototype.prototype === Object.prototype; // true
I'm wondering, what fooInst.prototype exactly is. In Chromes inspector it seems to be some kind of Foo with an constructor property. But all sources I read about prototypes state that fooInst.prototype === Foo.prototype should be true.
So my question: how exactly does JS handle the prototype chain. What exactly happens when I call new Foo.
Thanks in advance!
Edit
So I found, that (in Chrome) Object.getPrototypeOf(fooInst) === Foo.prototype; is true, but Object.getPrototypeOf(fooInst) === Object.getPrototypeOf(Foo) is false. Why that?
I'm wondering, what fooInst.prototype exactly is.
It is undefined.
fooInst.prototype === undefined; // true
Only functions have an automatic .prototype property. Objects do not.
If you create an object using a constructor, like:
var fooInst = new Foo('test');
...then fooInst will have an internal reference to Foo.prototype, but there's no standard property to get Foo.prototype from fooInst.
That said, there is a non-standard property that is supported in some JavaScript environments for referencing the prototype object.
fooInst.__proto__ === Foo.prototype; // true (if __proto__ supported)
Also, there is a method provided by ECMAScript 5 that can be used.
Object.getPrototypeOf( fooInst ) === Foo.prototype; // true
That internal reference from an object to its prototype object can be just the first in a chain of such references.
The prototype object likely has its own prototype object that is referenced. (In basic cases, this will be Object.prototype, or with longer chains, Object.prototype may be further down the chain.)
Object.prototype itself references null as its prototype. This ends the chain.
You should note that the internal reference from an object to its prototype object does not change if you change the .prototype object of the constructor function. It is a reference that exists for the life of the object.
var Foo = function(s) {
this._bar = s;
};
var fooInst = new Foo('test');
Object.getPrototypeOf( fooInst ) === Foo.prototype; // true
// Change the prototype object of Foo
Foo.prototype = { some:'object' };
Object.getPrototypeOf( fooInst ) === Foo.prototype; // false
Your first assumption:
Foo.prototype === Function.prototype;
Is not right, I think you are mixing up the concept of the [[Prototype]] internal property that all objects have, and makes the "link" of the prototype chain, and the prototype property that function objects have.
The above comparison will produce false because the value of the Foo.prototype property is a new object, created at the time you created the Foo function.
This object is initialized whenever you create a function object, it inherits from Object.prototype and it has a property, named constructor that points back to the function (Foo.prototype.constructor === Foo), and it's used when you call your function as a constructor.
Now, if we talk about the [[Prototype]] internal property, you are right, the [[Prototype]] of your Foo function is Function.prototype in other words, Foo inherits from Function.prototype, e.g.:
Object.getPrototypeOf(Foo) === Function.prototype; // true
Foo instanceof Function; // true
Foo.__proto__ === Function.prototype; // true
About fooInst this object was created in a new expression, when you used your Foo function as a constructor, this new object is produced, and it inherits from Foo.prototype, (its internal [[Prototype]] property points to Foo.prototype).
It doesn't have a prototype property, since this property is only meaningful for function objects.
See also:
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With