1.call()和apply()简介
在JavaScript中,每个函数对象都带有call()和apply()方法,即Function.prototype.call()和Function.prototype.apply(),这两个方法都是挂载在原型上的。
MDN官方解释如下:
call:
**call()**
方法使用一个指定的this
值和单独给出的一个或多个参数来调用一个函数。
apply:
**
apply()
**方法调用一个具有给定this
值的函数,以及以一个数组(或类数组对象)的形式提供的参数。
通过官网的解释,大家可能对这两个方法有了一个大致的了解,其实简单来说,call和apply两个方法最主要的作用就是改变this指向。
2. call()和apply()使用方法
call:
function.call(thisArg, arg1, arg2, ...)
apply:
func.apply(thisArg, [argsArray])
参数说明:
thisArg: 函数在运行时的this值,如果函数处于非严格模式下,则指定为 null
或 undefined
时会自动替换为指向全局对象。
arg1, arg2, ...和_[argsArray_]:函数接收的参数列表。
3.this指向简单示例
代码示例:
<script> let obj1 = { name: "张三", age: 24, user: function (args) { console.log("姓名:", this.name); console.log("年龄:", this.age); console.log("参数", args); } } let obj2 = { name: "李四", age: 30, user: function () { console.log("姓名:", this.name); console.log("年龄:", this.age); console.log("参数", args); } } // 正常的调用 obj1.user('我是参数'); obj2.user('我是参数'); </script>
输出结果
输出结果
上段代码中声明了两个对象obj1和obj2,对象中包括了一些常规属性和一个方法属性。然后在最后分别调用了对象中的两个方法,方法中的this指向不出意外的指向了我们的调用者,方法中的name和age就是当前对象中声明的值
4.使用call()和apply()方法改变this指向
代码示例:
<script> let obj1 = { name: "张三", age: 24, user: function (args) { console.log("姓名:", this.name); console.log("年龄:", this.age); console.log("参数", args); } } let obj2 = { name: "李四", age: 30, user: function (args) { console.log("姓名:", this.name); console.log("年龄:", this.age); console.log("参数", args); } } // 正常的调用 // obj1.user('我是参数'); // obj2.user('我是参数'); // 改变this指向 obj1.user.call(obj2, "我是参数"); // 使用call方法改变 obj2.user.apply(obj1, ["我是参数"]); // 使用apply方法改变 </script>
输出结果:
输出结果
由上面输出结果可以看出,结果恰好和正常的this指向的结果相反,因为我们使用call方法和apply方法改变了this指向,即当我们调用obj1.user方法时,将this的指向变为了obj2,所以方法中答应出了obj2中的属性值。
5.call与apply的区别
MDN上有这样一段让读者注意的话:
注意:call()方法的作用和 apply() 方法类似,区别就是
call()
方法接受的是参数列表,而apply()
方法接受的是一个参数数组。
由上面可以得出:两个方法没有什么区别,唯一的区别就是接收的参数不同,一个接收参数列表,一个接收参数数组,才上面的代码示例中也可以看出来。
总结:
call()和apply()两个方法很相似,但是又有些许的不同,在开发中可能很多小伙伴没有用过,但是其实它们的使用场景是很多的,比如:Math.max.apply(null, array)等。