apply、call、bind
这三个方法按照正式的说,就是这些方法能劫持另外一个对象的方法,继承另外一个对象的属性。通俗的说就是可以改变this的指向。
1、apply
1. 基本使用
语法:apply(T,A)
T
:改变后this的指向
A
:传递的参数,数组类型
具体演示:
window.name = 'window'
let parent1 = {
name: 'parent'
}
function child1() {
console.log(this.name);
}
child1() // window
child1.apply(parent1) // parent
当我们没有改变this指向时,child()函数的this是window,因为child()默认被window调用。
但是当我利用apply让this指向parent1时,this.name就是parent1的name。
2. 类的继承
当然,apply也常被用来作为类的继承:
function Parent1(name, sex) {
this.name = name
this.sex = sex
}
function Child2(name, sex, age) {
Parent1.apply(this, arguments) // 参数以数组类型传递,参数顺序要对应
this.age = age
}
let a = new Child2('lis', '男', 22)
console.log(a);
2、call
1. 基本使用
语法:call(T,arg1,arg2,arg3...)
T
:改变后this的指向
arg1、2、3...
:传递的参数,逗号隔开
具体演示:
window.name = 'window'
let parent1 = {
name: 'parent1'
}
function child1() {
console.log(this.name);
}
child1() // window
child1.call(parent1) // parent1
原理和上面apply一样,将child()函数的this指向了parent1
2. 类的继承
类的继承:
let Parent2 = function (name, sex) {
this.name = name
this.sex = sex
}
let Child2 = function (name, sex, age) {
Parent2.call(this, name, sex) // 参数分开传递,以逗号隔开
this.age = age
}
let a = new Child2('lis', '男', 22)
console.log(a);
3、bind
1. 基本使用
语法:bind(T,arg1,arg2,arg3...)
T
:改变后this的指向
arg1、2、3...
:传递的参数,逗号隔开
具体演示:
window.name = 'window'
let parent1 = {
name: 'parent1'
}
function child1() {
console.log(this.name);
}
child1() // window
console.log(child1.bind(parent1)); // 被改变this的child1函数
child1.bind(parent1)(); // parent1
我们可以看到执行bind之后,会返回一个函数。我们可以看出来他就是child1函数,但是我们执行这个函数就会发现,实际上它的this已经改变,指向了parent1。
2. 类的继承
类的继承:
function Parent2(name, sex) {
this.name = name
this.sex = sex
}
function Child2(name, sex, age) {
Parent2.bind(this, name, sex)()
this.age = age
}
let a = new Child2('lis', '男', 22)
console.log(a);
4、区别
1. apply和call
apply和call作用上基本上是一致的,它们最大的区别就是参数传递方式的不同。它们第一个参数都是this即将指向的对象,但是aplly的第二个参数接收一个数组,数组中是方法执行时要传递的参数,而call是将参数以逗号隔开,分开传递。
2. bind和call、apply
bind和call传递参数的方式一致,但是通过上面的代码我们很容易可以看出,bind最后会返回一个已经修改过this指向的函数,我们需要手动执行,而call和apply会立即执行。所以call和apply不仅可以用来改变this指向也可以用来立即执行一个函数。
bind和apply相较于call则由多了一个参数传递方式不同的区别。