浅谈JavaScript中的call和apply

时间:2022-10-23 14:48:12

语法

fun.apply(thisArg, [argsArray])

fun.call(thisArg, arg1, arg2, ...)

apply 接收两个参数,第一个参数指定了函数体内this对象的指向,第二个参数为带下标的集合,这个集合可以为数组,也可以为类数组,apply 方法把这个集合总的元素传递给被调用的函数。

call是包装在apply上的语法糖,如果知道具体多少个参数,可以使用call来传递参数,方便表达形参和实参的对应关系。

往往apply和call容易记混淆,不妨使用联想记忆:

apply ->array  //字母开头都是a

只要看到apply就会想到接收的是array。apply接收数组或类数组对象,而call接收参数列表。

用途

1.改变this的指向

简单来说就是当 fun函数运行时,指定this的值 为 thisArg。

var a = 10,b = 20;
function add(c,d){
return this.a + this.b + c +d;
} var o ={a:1,b:2}; add(3,4); // 10 + 20 + 3 + 4 = 37
add.call(o,3,4); // 1 + 2 + 3 + 4 = 10
add.apply(o,[3,4]); // 1 + 2 + 3 + 4 = 10

上面的例子可以看出

当直接调用add时,this指向 window;
当使用call、apply时,this指向了o;

2.借用其他对象方法

当一个object对象没有某个方法,可以借助call或apply用其它对象的方法来实现。

function Cat(){

}
Cat.prototype = {
voice:"miao~miao~",
say: function () {
console.log("I can say "+ this.voice);
}
};
var writeCat = new Cat();
writeCat.say(); // I can say miao~miao~ //dog
var yellowDog = {voice:"wang~wang~"};
writeCat.say.call(yellowDog); // I can say wang~wang~

关于thisArg

thisArg 是对象类型。
当指定的thisArg不是对象类型时,会先转成相应的对象类型,再进行后续程序。

function foo(x,y){
console.log(x,y,this);
} foo.call(100,1,2); // 1 2 Number {}
foo.call(true,1,2); // 1 2 Boolean {}
foo.call('string',1,2); // 1 2 String { 0="s", 1="t", 2="r", 更多...}
foo.call(null); //undefined undefined Window
foo.call(undefined); //undefined undefined Window

当指定为null和undefined时,函数内的this会指向默认的宿主对象,在浏览器里是Window,但当在严格模式时,则不进行转化。