apply、bind、call基本概念

389 阅读2分钟

前言

applybindcall大家在初次见到的的时候难免会疑惑,好纠结呀,都没用过。我可以告诉大家,咱们就学一个,学会这一个,其他两个就迎刃而解了。咱就学callcall学完其他两个就简单了。

什么是call

call是一个方法,它是函数的方法。我们来看以下代码:

function fun() {
    console.log("hello world")
};
// call可以调用方法
fun.call();

输出为:

C01.png

我们可以看到call直接被调用了。说明函数的call方法可以直接调用函数。 除了可直接被调用往外,call还可以改变this指向,我们来看以下代码:

function fun() {
    console.log(this)
    console.log(this.name);
};
let cat = {
    name"喵喵"
}
fun(); // 空
//call可以改变函数中this 指向
fun.call(cat); // 喵喵

C02.png

我们可以看到第一次打印出来的结果是:this是指Windowthis.name打印出来是 第二次call运行输出的结果是:this指向的是cat对象,this.name打印出来是喵喵(cat的属性)

call深入了解

this指向修改

接下来我们实现一个this指向的更改,我们来看以下代码:

let dog = {
    name"旺财",
    sayName() {
        console.log("我是" + this.name);
    }
}
let cat = {
    name"喵喵"
}
// call可以调用函数,cal1可以改变函数中this
//指向
dog.sayName() // 我是旺财
dog.sayName.call(cat); // 我是喵喵

输出为:

C03.png

我们可以看到当sayName方法被直接调用时,输出为我是旺财 当我们用call方法把this指向更改为cat的时候,sayName方法就输出为我是喵喵

call的其他传参

我们在dog对象中新添加一个方法eat:

eat(food) {
   console.log('吃' + food)
}

正常调用的话:

dog.eat('骨头'// 吃骨头

如果换成call调用我们就需要将传入的参数作为第二参数传入如下:

dog.eat.call(cat,'鱼'); // 吃鱼

当我们有更多参数时候,我们可以在call方法的 2、3、4...n个参数中传入:

dog.eat.call(cat,'鱼','老鼠'); // 吃鱼、老鼠 

所以call的第一个参数为改变this指向的对象,第2到n个参数为所传得参数

apply、bind、call的区别

apply的参数列表是数组传入的,具体用法如下:

dog.eat.apply(cat,['鱼','老鼠']); // 吃鱼、老鼠 

bind和call的区别在于bind不会直接调用方法,方法将是它的一个返回:

let fn = dog.eat.bind(cat,'鱼','老鼠'); 
fn(); // 吃鱼、老鼠 

整理下这三者的区别在于:

区别项applybindcall
第2参数数组按参数传按参数传
方法调用立即调用返回方法立即调用