Objects

Objects → Represent Properties, Methods[Functionalities]

Properties → Attribute: Color, weight etc.

Method → Actions, functions

Prototypes

A prototype provide a mechanism for object inheritance.

JavaScript follows a prototype-based inheritance model → meaning that objects inherit properties and methods from other objects.

Prototype Inheritance

function Person(name) {
    this.name = name;
}

Person.prototype.greet = function() {
    console.log(`Hello, my name is ${this.name}`);
};

const person1 = new Person("Aman");

person1.greet(); // Output: Hello, my name is Aman

The Prototype Chain

When you access a property of an object, JavaScript first checks if the object has that property. If not, it looks up the prototype chain until it reaches null.

function Person(name) {
    this.name = name;
}

Person.prototype.greet = function () {
    console.log(`Hello, my name is ${this.name}`);
};

const john = new Person("John");
john.greet();  // Output: Hello, my name is John

console.log(john.__proto__ === Person.prototype); // true
console.log(Person.prototype.__proto__ === Object.prototype); // true
console.log(Object.prototype.__proto__ === null); // true

DRY principle - Do not repeat yourself

// Prototype Chaining

const person1 = {
  "First Name": "Sandeep",
  "Last Name": "Patel",
  getFullname: function () {
    if (this["First Name"] !== undefined) return `${this["First Name"]} ${this["Last Name"]}`;

    return this["First Name"];
  }

}

const person2 = {
  "First Name": "Amit",
  "Last Name": "Singh",
  // getFullname: function () {
  //   return `${this["First Name"]} ${this["Last Name"]}`
  // }

};

// Bad Practice: Is Internal work           
person2.__proto__ = person1;
// person1.__proto__ = null; 

// DRY principle - Do not repeat yourself

console.log("Person 1: ", person1.getFullname()); // Person 1:  Sandeep Patel
console.log("Person 2: ", person2.getFullname()); // Person 2:  Amit Singh
console.log(person2.toString()); // [object Object]

Object Prototypes

Object has an internal link (__proto__) to its prototype object.

const obj = {};
console.log(obj.__proto__ === Object.prototype); // true

// Even arrays and functions inherit from Object.prototype✅

console.log([].__proto__ === Array.prototype); // true
console.log(Array.prototype.__proto__ === Object.prototype); // true

Modifying Prototypes

Do's (Safe Modifications)