Trong JavaScript, các phương thức call()
, apply()
, và bind()
đều được sử dụng để thiết lập giá trị của từ khóa this
trong một hàm, cho phép bạn kiểm soát ngữ cảnh khi hàm được gọi. Mặc dù chúng có mục đích tương tự nhau, nhưng cách sử dụng và hành vi của chúng có những khác biệt nhỏ.
call()
Phương thức call()
gọi một hàm với một giá trị this
cụ thể, và bạn có thể truyền các đối số vào hàm đó lần lượt.
Cú pháp:
func.call(thisArg, arg1, arg2, ...);
thisArg
: Giá trị mà this
sẽ được gán khi hàm được thực thi.arg1, arg2, ...
: Các đối số được truyền vào hàm.Ví dụ:
function greet(greeting, name) { console.log(greeting + ', ' + name + '!'); } greet.call(null, 'Hello', 'Alice'); // 'Hello, Alice!'
Ở đây, phương thức call()
được sử dụng để gọi hàm greet()
với giá trị this
là null
và truyền hai đối số là 'Hello'
và 'Alice'
.
apply()
Phương thức apply()
tương tự như call()
, nhưng thay vì truyền các đối số riêng lẻ, bạn truyền chúng dưới dạng một mảng.
Cú pháp:
func.apply(thisArg, [argsArray]);
thisArg
: Giá trị mà this
sẽ được gán khi hàm được thực thi.argsArray
: Một mảng chứa các đối số cần truyền vào hàm.Ví dụ:
function greet(greeting, name) { console.log(greeting + ', ' + name + '!'); } greet.apply(null, ['Hi', 'Bob']); // 'Hi, Bob!'
Ở đây, apply()
truyền các đối số dưới dạng một mảng ['Hi', 'Bob']
.
call()
và apply()
call()
: Các đối số được truyền lần lượt.apply()
: Các đối số được truyền dưới dạng mảng.Ví dụ so sánh:
function sum(a, b) { return a + b; } console.log(sum.call(null, 2, 3)); // 5 console.log(sum.apply(null, [2, 3])); // 5
bind()
Phương thức bind()
không thực thi hàm ngay lập tức mà trả về một bản sao của hàm với giá trị this
được cố định (bound) vào giá trị cụ thể và các đối số có thể được truyền sẵn nếu muốn. Hàm trả về có thể được gọi sau này.
Cú pháp:
let boundFunc = func.bind(thisArg, arg1, arg2, ...);
thisArg
: Giá trị mà this
sẽ được gán khi hàm được thực thi.arg1, arg2, ...
: Các đối số sẽ được cố định cho hàm.Ví dụ:
let person = { name: 'Charlie', greet: function() { console.log('Hello, ' + this.name); } }; let greetCharlie = person.greet.bind(person); greetCharlie(); // 'Hello, Charlie'
Trong ví dụ này, bind()
tạo một hàm mới greetCharlie
với this
được gán cố định vào đối tượng person
. Hàm này có thể được gọi sau đó, và giá trị của this
luôn là person
.
Ví dụ với đối số:
function multiply(a, b) { return a * b; } let double = multiply.bind(null, 2); console.log(double(5)); // 10
Ở đây, bind()
tạo một hàm double
mà giá trị a
luôn là 2, chỉ cần truyền b
khi gọi hàm sau đó.
call()
, apply()
, và bind()
Phương thức | Thực thi ngay lập tức? | Truyền đối số | Mục đích |
---|---|---|---|
call() | Có | Các đối số được truyền lần lượt | Gọi hàm với this và đối số cụ thể. |
apply() | Có | Đối số truyền dưới dạng mảng | Gọi hàm với this và đối số cụ thể trong mảng. |
bind() | Không | Đối số được cố định trước | Trả về một hàm mới với this và đối số cố định. |
call()
và apply()
: Khi bạn cần thực thi một hàm ngay lập tức với một ngữ cảnh this
cụ thể. Dùng call()
nếu bạn có các đối số riêng lẻ, dùng apply()
nếu bạn có các đối số trong một mảng.bind()
: Khi bạn cần tạo một phiên bản của hàm có this
và/hoặc đối số cố định, đặc biệt hữu ích khi truyền hàm như là callback mà bạn muốn giữ ngữ cảnh của this
.Những phương thức này là công cụ mạnh mẽ giúp kiểm soát cách hàm hoạt động với this
và các đối số, giúp bạn dễ dàng làm việc với các hàm trong các trường hợp đặc biệt hoặc phức tạp.