JavaScript Prototypes
What is a prototype in JavaScript?
A prototype in JavaScript is an object that is associated with every function and object by default. It allows for inheritance and the sharing of properties and methods among objects. When you attempt to access a property or method on an object, JavaScript looks up the prototype chain to find it.
How does the prototype chain work?
The prototype chain is a series of links between objects that enables inheritance. If a property or method is not found on an object, JavaScript checks the object's prototype, then the prototype's prototype, and so on, until it reaches Object.prototype, which is the top of the chain.
function Animal(name) {
this.name = name;
}
Animal.prototype.speak = function() {
console.log(`${this.name} makes a noise.`);
};
const dog = new Animal('Rex');
dog.speak(); // Rex makes a noise.
console.log(dog.toString()); // Inherited from Object.prototype
How do you create a prototype in JavaScript?
You can create a prototype by defining methods or properties on the prototype property of a constructor function or using the class syntax.
// Using constructor function
function Dog(name) {
this.name = name;
}
Dog.prototype.bark = function() {
console.log(`${this.name} barks.`);
};
const dog = new Dog('Rex');
dog.bark(); // Rex barks.
// Using class syntax
class Cat {
constructor(name) {
this.name = name;
}
meow() {
console.log(`${this.name} meows.`);
}
}
const cat = new Cat('Whiskers');
cat.meow(); // Whiskers meows.
What is the difference between the prototype property and the __proto__ property?
The prototype property is used to set up inheritance for functions and is available on constructor functions, whereas the __proto__ property is an internal property of all objects that points to the object's prototype. It is a way to access the prototype chain, but it is not recommended for direct use.
function Person(name) {
this.name = name;
}
const alice = new Person('Alice');
console.log(Person.prototype); // Prototype property of the constructor
console.log(alice.__proto__); // Points to Person.prototype
How do you add a property to an object's prototype?
You can add a property to an object's prototype by assigning it directly to the prototype property of the constructor function.
function Vehicle(make, model) {
this.make = make;
this.model = model;
}
// Adding a method to the prototype
Vehicle.prototype.getInfo = function() {
return `${this.make} ${this.model}`;
};
const car = new Vehicle('Toyota', 'Corolla');
console.log(car.getInfo()); // Toyota Corolla
How do you check if an object inherits from a prototype?
You can use the instanceof operator to check if an object is an instance of a specific constructor function, which checks the prototype chain.
function Animal(name) {
this.name = name;
}
const dog = new Animal('Rex');
console.log(dog instanceof Animal); // true
console.log(dog instanceof Object); // true
What is the role of Object.create() in prototype-based inheritance?
Object.create() creates a new object with the specified prototype object and properties. It is often used to set up inheritance without invoking a constructor function.
const animal = {
speak() {
console.log(`${this.name} makes a noise.`);
}
};
const dog = Object.create(animal);
dog.name = 'Rex';
dog.speak(); // Rex makes a noise.
What are constructor functions and how do they relate to prototypes?
Constructor functions are special functions used to create objects. When called with the new keyword, they create an instance of the object with access to the properties and methods defined on the constructor's prototype.
function Car(make, model) {
this.make = make;
this.model = model;
}
Car.prototype.getInfo = function() {
return `${this.make} ${this.model}`;
};
const myCar = new Car('Honda', 'Civic');
console.log(myCar.getInfo()); // Honda Civic
How can you override a method defined on a prototype?
You can override a method by defining a new method with the same name on the instance or in the subclass, effectively replacing the inherited behavior.
function Animal(name) {
this.name = name;
}
Animal.prototype.speak = function() {
console.log(`${this.name} makes a noise.`);
};
function Dog(name) {
Animal.call(this, name);
}
// Inherit from Animal
Dog.prototype = Object.create(Animal.prototype);
Dog.prototype.constructor = Dog;
// Override speak method
Dog.prototype.speak = function() {
console.log(`${this.name} barks.`);
};
const dog = new Dog('Rex');
dog.speak(); // Rex barks.