在 JavaScript 中,apply 和 call 是函數的兩個方法,用於顯式設置函數的 this 值,並傳遞參數來執行函數。它們的主要區別是傳遞參數的方式不同:
假設有一個通用的函數,我們希望在不同對象上使用它。
function greet(greeting, punctuation) {
console.log(`${greeting}, ${this.name}${punctuation}`);
}
const person1 = { name: "Alice" };
const person2 = { name: "Bob" };
greet.call(person1, "Hello", "!"); // Hello, Alice!
greet.apply(person2, ["Hi", "."]); // Hi, Bob.
借用其他對象的方法來處理當前對象。
const arrayLike = {
0: "a",
1: "b",
2: "c",
length: 3
};
// 使用 Array.prototype 方法處理類數組對象
const result = Array.prototype.slice.call(arrayLike);
console.log(result); // ["a", "b", "c"]
當參數已經是數組時,apply 可以直接使用它。
const numbers = [5, 6, 2, 3, 7];
// 使用 Math.max 和 apply 找出數組中的最大值
const max = Math.max.apply(null, numbers);
console.log(max); // 7
// 使用 Math.min 和 apply 找出數組中的最小值
const min = Math.min.apply(null, numbers);
console.log(min); // 2
用 apply 來執行構造函數。
function Person(name, age) {
this.name = name;
this.age = age;
}
function createNew(Constructor, args) {
const obj = Object.create(Constructor.prototype);
Constructor.apply(obj, args);
return obj;
}
const person = createNew(Person, ["Alice", 25]);
console.log(person.name); // Alice
console.log(person.age); // 25
用 call 和 apply 動態地修改函數行為。
function sum(a, b, c) {
return a + b + c;
}
// 使用 call 傳遞逐個參數
console.log(sum.call(null, 1, 2, 3)); // 6
// 使用 apply 傳遞數組參數
console.log(sum.apply(null, [1, 2, 3])); // 6
當你已經知道參數一個一個地傳入,使用 call:
someFunction.call(context, arg1, arg2, arg3);
當參數以數組形式存在時,使用 apply:
someFunction.apply(context, [arg1, arg2, arg3]);
兩者用途非常相似,可以根據數據形式選擇合適的方法。