The Magic of this, call(), apply(), and bind() in JavaScript
1. What is "this"?
In the simplest terms, this refers to the object that is currently executing the function.
Think of it like the word "me" in a conversation. If I say, "I am going home," the word "I" refers to Prakash. If you say, "I am going home," the word "I" refers to you. The meaning of the word changes depending on who is speaking.
Inside a Normal Function
If you call a function in the global scope (not inside an object), this usually refers to the global object (the window in a browser).
JavaScript
function showContext() {
console.log(this);
}
showContext(); // Logs the Window object
Inside an Object
When a function is a method inside an object, this refers to the object itself.
JavaScript
const restaurant = {
name: "Jaipur Delights",
greet: function() {
return "Welcome to " + this.name;
}
};
console.log(restaurant.greet()); // Output: Welcome to Jaipur Delights
2. Explicit Binding: Taking Control
Sometimes, we want to force a function to use a specific object as its this context. This is called Explicit Binding. We use three main tools for this: call, apply, and bind.
Imagine you have a billing system. You want to use the same "print receipt" logic for different restaurants without rewriting the code.
The call() Method
call() invokes the function immediately and allows you to pass arguments one by one.
JavaScript
function generateBill(tax, tip) {
const total = this.price + tax + tip;
console.log("Total at " + this.storeName + ": " + total);
}
const cafe = { storeName: "Central Perk", price: 500 };
// We "call" the function and tell it to use 'cafe' as its context
generateBill.call(cafe, 50, 20);
The apply() Method
apply() is almost identical to call(), but it takes arguments as an array. This is perfect when you have a list of data and you don't know how many items are in it.
JavaScript
const argumentsArray = [50, 20];
// Using apply instead of call
generateBill.apply(cafe, argumentsArray);
The bind() Method
Unlike the first two, bind() does not run the function immediately. Instead, it creates a copy of the function with the context locked in, so you can use it later.
JavaScript
const printCafeBill = generateBill.bind(cafe);
// Later in the code...
printCafeBill(50, 20);
3. Comparison: Call vs Apply vs Bind
Final Quest: The Method Borrower
For this assignment, we will create a person object and "borrow" their greeting for another person.
Assignment Implementation
JavaScript
// 1. Create an object with a method using 'this'
const person1 = {
firstName: "Prakash",
lastName: "Jha",
introduce: function(city, country) {
console.log("I am " + this.firstName + " " + this.lastName + " from " + city + ", " + country);
}
};
const person2 = {
firstName: "Aarav",
lastName: "Sharma"
};
// 2. Borrow that method using call()
person1.introduce.call(person2, "Jaipur", "India");
// 3. Use apply() with array arguments
const locationData = ["Mumbai", "India"];
person1.introduce.apply(person2, locationData);
// 4. Use bind() and store the function
const greetAarav = person1.introduce.bind(person2, "Delhi", "India");
greetAarav();
By mastering these three methods, you have gained full control over the execution context in JavaScript. You are no longer at the mercy of how a function is called; you are the one deciding what this represents.