了解 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 中的调用和应用方法

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

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

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

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

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