Hiểu sự khác biệt giữa `call` và `apply` trong JavaScript

Hiểu sự khác biệt giữa `call` và `apply` trong JavaScript
JavaScript

Các phương thức gọi hàm trong JavaScript

JavaScript cung cấp một số cách để gọi hàm, hai trong số đó là `Function.prototype.call()` và `Function.prototype.apply()`. Cả hai phương thức đều dùng để gọi các hàm có giá trị `this` và đối số được chỉ định, nhưng chúng khác nhau về cách truyền các đối số này.

Bài viết này nhằm mục đích khám phá sự khác biệt giữa `gọi` và `áp dụng`, ý nghĩa về hiệu suất của chúng và các tình huống trong đó cái này có thể được ưu tiên hơn cái kia. Cuối cùng, bạn sẽ hiểu rõ hơn về thời điểm nên sử dụng `gọi` hoặc `áp dụng` trong mã JavaScript của mình.

Khám phá sự khác biệt giữa `call` và `apply` trong JavaScript

Ví dụ về giao diện người dùng JavaScript

// Example of Function.prototype.call()
const person = {
  fullName: function() {
    return this.firstName + " " + this.lastName;
  }
};

const person1 = {
  firstName: "John",
  lastName: "Doe"
};

console.log(person.fullName.call(person1)); // John Doe

Hiểu hiệu suất của `call` so với `apply` trong JavaScript

Ví dụ về giao diện người dùng JavaScript

// Example of Function.prototype.apply()
const person = {
  fullName: function(city, country) {
    return this.firstName + " " + this.lastName + ", " + city + ", " + country;
  }
};

const person2 = {
  firstName: "Jane",
  lastName: "Doe"
};

console.log(person.fullName.apply(person2, ["Oslo", "Norway"])); // Jane Doe, Oslo, Norway

So sánh `call` và `apply` cho Lệnh gọi hàm trong JavaScript

Ví dụ về phần cuối của Node.js

const person = {
  fullName: function(city, country) {
    return this.firstName + " " + this.lastName + ", " + city + ", " + country;
  }
};

const person3 = {
  firstName: "Alice",
  lastName: "Smith"
};

function printName(method) {
  if (method === 'call') {
    console.log(person.fullName.call(person3, 'Paris', 'France'));
  } else if (method === 'apply') {
    console.log(person.fullName.apply(person3, ['Paris', 'France']));
  }
}

printName('call');  // Alice Smith, Paris, France
printName('apply'); // Alice Smith, Paris, France

Lựa chọn giữa `gọi` và `áp dụng` trong phát triển JavaScript

Phân tích hiệu suất JavaScript

const iterations = 1000000;
const person = {
  fullName: function(city, country) {
    return this.firstName + " " + this.lastName + ", " + city + ", " + country;
  }
};
const person4 = {
  firstName: "Bob",
  lastName: "Brown"
};

console.time('call');
for (let i = 0; i < iterations; i++) {
  person.fullName.call(person4, 'Berlin', 'Germany');
}
console.timeEnd('call');

console.time('apply');
for (let i = 0; i < iterations; i++) {
  person.fullName.apply(person4, ['Berlin', 'Germany']);
}
console.timeEnd('apply');

Hiểu biết sâu hơn về cuộc gọi và áp dụng các Phương thức trong JavaScript

Ngoài cách sử dụng cơ bản, Function.prototype.call()Function.prototype.apply() có một số trường hợp sử dụng nâng cao có thể nâng cao khả năng lập trình JavaScript của bạn. Một trường hợp sử dụng như vậy là mượn phương thức, trong đó các phương thức từ đối tượng này được đối tượng khác mượn. Điều này đặc biệt hữu ích khi bạn có một đối tượng cần sử dụng một phương thức từ một đối tượng khác mà không có sự kế thừa. sử dụng call()apply(), bạn có thể tạm thời mượn các phương thức và thực thi chúng trong ngữ cảnh của các đối tượng khác nhau, từ đó nâng cao khả năng sử dụng lại mã và giảm sự dư thừa.

Một khía cạnh quan trọng khác cần xem xét là việc sử dụng apply() đối với các hàm biến phân—các hàm chấp nhận số lượng đối số thay đổi. Khi bạn có một mảng các đối số và bạn cần chuyển chúng cho một hàm không chấp nhận mảng, apply() trở nên vô cùng tiện dụng. Mặt khác, call() có thể hữu ích trong các tình huống trong đó hiệu suất là rất quan trọng và số lượng đối số đã được biết và cố định. Bằng cách hiểu những sắc thái này, nhà phát triển có thể đưa ra quyết định sáng suốt hơn về thời điểm sử dụng call() đấu với apply(), tối ưu hóa mã của họ để có cả khả năng đọc và hiệu suất.

Câu hỏi thường gặp về lệnh gọi và áp dụng trong JavaScript

  1. Sự khác biệt chính giữa call()apply()?
  2. call() chấp nhận các đối số riêng lẻ, trong khi apply() chấp nhận các đối số như một mảng.
  3. Có thể call()apply() được sử dụng thay thế cho nhau?
  4. Đúng, họ có thể đạt được kết quả tương tự, nhưng sự lựa chọn phụ thuộc vào cách cấu trúc các đối số.
  5. Khi nào tôi nên ưu tiên apply() qua call()?
  6. Sử dụng apply() khi bạn có một mảng đối số hoặc số lượng đối số thay đổi.
  7. Có sự khác biệt về hiệu suất giữa call()apply()?
  8. Sự khác biệt về hiệu suất là không đáng kể trong hầu hết các trường hợp, nhưng call() có thể nhanh hơn một chút với số lượng đối số cố định.
  9. Làm thế nào để call()apply() xử lý this bối cảnh?
  10. Cả hai phương pháp đều đặt rõ ràng this bối cảnh cho việc gọi hàm.
  11. Tôi có thể sử dụng không? call()apply() với các hàm tạo?
  12. Không, chúng không phù hợp với các hàm khởi tạo vì chúng không tạo ra các phiên bản mới.
  13. Một số trường hợp sử dụng nâng cao là gì call()apply()?
  14. Chúng rất hữu ích cho việc mượn phương thức và xử lý các hàm biến đổi.
  15. Làm thế nào call() cải thiện khả năng đọc mã?
  16. call() làm cho việc gọi hàm trở nên rõ ràng hơn khi số lượng đối số được biết và cố định.
  17. Có thể apply() xử lý một số lượng đối số không xác định?
  18. Đúng, apply() là lý tưởng cho các hàm cần xử lý số lượng đối số thay đổi.

Suy nghĩ cuối cùng về các phương thức gọi hàm

Tóm lại, cả hai callapply các phương thức là những công cụ mạnh mẽ trong JavaScript để gọi các hàm với một phạm vi được chỉ định this giá trị. Việc lựa chọn giữa chúng phụ thuộc phần lớn vào cách bạn muốn truyền đối số cho hàm. Trong khi call là tốt nhất khi xử lý một số lượng đối số cố định, apply tỏa sáng khi xử lý mảng hoặc số lượng đối số không xác định. Hiểu được những sắc thái này giúp viết mã hiệu quả và dễ đọc hơn, cuối cùng dẫn đến thực tiễn lập trình JavaScript tốt hơn.