We can do the same using {__proto__:...}
:
var Animal = {
speak() {
console.log(this.name + ' makes a noise.');
}
};
var Dog={
__proto__: Animal
}
Dog.name='Mitzie'
Dog.speak(); // Mitzie makes a noise.
The {__proto__: Animal}
is a way of defining prototype chain
. Here, this is {__proto__: {speak:function(){...}}
as defined in Animal.
To understand this let's see the chain in steps. When we did Dog.speak()
js can't find function speak
inside Dog. So it goes up the chain once and finds speak
inside Animal. As expected this outputs "Mitzie makes a noise.".
Conceptually, Object.setPrototypeOf(Dog.prototype, Animal)
is the same as Dog.prototype.__proto__=Animal
. We call this setting Dog.prototype.[[Prototype]]
to Animal. The [[Prototype]]
is a link pointing to an object one step up the chain.
var Animal=function() {}
Animal.prototype.speak=function() {
console.log(this.name + ' makes a noise.');
}
var Dog=function(name) {
this.name=name
}
// set up prototype chain
Dog.prototype.__proto__=Animal.prototype
var d = new Dog('Mitzie');
d.speak(); // Mitzie makes a noise.
Here is your example replaced with using __proto__
to define the prototype chain.
var Animal = {
speak() {
console.log(this.name + ' makes a noise.');
}
};
class Dog {
constructor(name) {
this.name = name;
}
}
//Object.setPrototypeOf(Dog.prototype, Animal);// If you do not do this you will get a TypeError when you invoke speak
Dog.prototype.__proto__=Animal
var d = new Dog('Mitzie');
d.speak(); // Mitzie makes a noise.
Lastly, you could just use class extends..
.
var Animal = class {
constructor(name) {
this.name=name
}
speak() {
console.log(this.name + ' makes a noise.');
}
};
class Dog extends Animal {
constructor(name) {
super(name)
}
}
var d = new Dog('Mitzie');
d.speak(); // Mitzie makes a noise.
As you can see this approach is the simplest so recommended ;)