了解 JavaScript 中“call”和“apply”之间的区别

了解 JavaScript 中“call”和“apply”之间的区别
JavaScript

JavaScript 中的函数调用方法

JavaScript 提供了多种调用函数的方法,其中两种是 `Function.prototype.call()` 和 `Function.prototype.apply()`。这两种方法都用于调用具有指定“this”值和参数的函数,但它们在传递这些参数的方式上有所不同。

本文旨在探讨“call”和“apply”之间的差异、它们的性能影响以及其中一个可能优于另一个的场景。最后,您将更清楚地了解何时在 JavaScript 代码中使用“call”或“apply”。

探索 JavaScript 中“call”和“apply”之间的差异

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

了解 JavaScript 中“call”与“apply”的性能

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

比较 JavaScript 中函数调用的“call”和“apply”

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

JavaScript 开发中“call”和“apply”之间的选择

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');

深入了解 JavaScript 中的调用和应用方法

除了它们的基本用法之外, Function.prototype.call()Function.prototype.apply() 有几个可以增强 JavaScript 编程的高级用例。其中一种用例是方法借用,其中一个对象的方法被另一个对象借用。当您有一个对象需要使用另一个对象的方法而无需继承时,这特别有用。使用 call()apply(),可以临时借用方法并在不同对象的上下文中执行它们,从而增强代码的可重用性并减少冗余。

另一个需要考虑的重要方面是使用 apply() 对于可变参数函数——接受可变数量参数的函数。当您有一个参数数组并且需要将它们传递给不接受数组的函数时, apply() 变得极其方便。另一方面, call() 在性能至关重要且参数数量已知且固定的情况下非常有用。通过了解这些细微差别,开发人员可以就何时使用做出更明智的决定 call() 相对 apply(),优化代码的可读性和性能。

有关 JavaScript 中调用和申请的常见问题

  1. 之间的主要区别是什么 call()apply()
  2. call() 单独接受参数,同时 apply() 接受数组形式的参数。
  3. call()apply() 可以互换使用吗?
  4. 是的,他们可以达到相同的结果,但选择取决于论点的结构。
  5. 我应该选择什么时候 apply() 超过 call()
  6. 使用 apply() 当你有一个参数数组或可变数量的参数时。
  7. 之间是否存在性能差异 call()apply()
  8. 在大多数情况下,性能差异可以忽略不计,但是 call() 使用固定数量的参数可以稍微快一些。
  9. 怎么办 call()apply() 处理 this 语境?
  10. 两种方法都显式设置 this 函数调用的上下文。
  11. 我可以用吗 call()apply() 与构造函数?
  12. 不,它们不适合构造函数,因为它们不创建新实例。
  13. 有哪些高级用例 call()apply()
  14. 它们对于方法借用和处理可变参数函数非常有用。
  15. 如何 call() 提高代码可读性?
  16. call() 当参数数量已知且固定时,使函数调用更加清晰。
  17. apply() 处理未知数量的参数?
  18. 是的, apply() 对于需要处理可变数量参数的函数来说是理想的选择。

关于函数调用方法的最终想法

总之,两者 callapply 方法是 JavaScript 中强大的工具,用于调用具有指定的函数 this 价值。它们之间的选择很大程度上取决于您希望如何将参数传递给函数。尽管 call 处理固定数量的参数时最好, apply 在处理数组或未知数量的参数时表现出色。了解这些细微差别有助于编写更高效、更易读的代码,最终带来更好的 JavaScript 编程实践。