In JavaScript, both call
and apply
are methods used to invoke a function with a specific this
context and arguments. The key difference lies in how they accept arguments:
1. call()
- Syntax:
function.call(thisArg, arg1, arg2, ...);
- Arguments:
Passed individually as a comma-separated list. - Use Case:
Use when you know the number of arguments upfront.
Example:
function greet(name, age) {
console.log(`Hello ${name}, you are ${age}. Context: ${this.title}`);
}
const context = { title: "Mr." };
greet.call(context, "Alice", 30);
// Output: "Hello Alice, you are 30. Context: Mr."
2. apply()
- Syntax:
function.apply(thisArg, [argsArray]);
- Arguments:
Passed as a single array (or array-like object). - Use Case:
Use when arguments are dynamic or already in an array.
Example:
const args = ["Bob", 25];
greet.apply(context, args);
// Output: "Hello Bob, you are 25. Context: Mr."
Key Differences
Feature | call() | apply() |
---|---|---|
Arguments | Comma-separated list (arg1, arg2 ) | Single array ([arg1, arg2] ) |
Performance | Slightly faster (no array unpacking) | Slightly slower (handles arrays) |
Use with ES6 | Can use spread operator:call(context, ...array) | Less common (spread replaces apply ) |
When to Use Which?
call()
:- Known number of arguments (e.g.,
func.call(ctx, 1, 2)
). - Borrowing methods (e.g.,
Array.prototype.slice.call(arrayLike)
). apply()
:- Dynamic arguments (e.g.,
Math.max.apply(null, [1, 2, 3])
). - Legacy code where spread operator (
...
) isn’t available.
Modern Alternative (ES6 Spread Operator)
With ES6, call
+ spread often replaces apply
:
const numbers = [5, 6, 2, 3, 7];
Math.max.call(null, ...numbers); // Same as Math.max.apply(null, numbers)
Common Use Cases
Borrowing Methods:
// Convert array-like object to array:
const arrayLike = { 0: "a", 1: "b", length: 2 };
const realArray = Array.prototype.slice.call(arrayLike); // ["a", "b"]
Chaining Constructors (Inheritance):
function Product(name, price) {
this.name = name;
this.price = price;
}
function Food(name, price) {
Product.call(this, name, price); // Inherits Product properties
this.category = 'food';
}
Summary
- Use
call()
for individual arguments. - Use
apply()
for arguments in an array. - Both set
this
and invoke the function immediately (unlikebind()
, which creates a new function). - Modern JavaScript often uses
call
with the spread operator (...
) instead ofapply
.
By understanding these differences, you can choose the right method for your use case!