call
call 是属于所有 Function 的方法,也就是 Function.prototype.call。
1 2
| fun.call(thisArg[,arg1[,arg2,…]]);
|
使用 call 调用函数并且指定 this
1 2 3 4 5 6 7 8 9
| var obj = { a: 1 } function foo(b, c){ this.b = b; this.c = c; console.log(this.a + this.b + this.c); } foo.call(obj,2,3); // 6
|
call 实现继承
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| function Person(name, age){ this.name = name; this.age = age; this.say = function(){ console.log(this.name + ":" + this.age); } } function Student(name, age, job){ Person.call(this, name ,age); this.job = job; this.say = function(){ console.log(this.name + ":" + this.age + " " + this.job); } } var me = new Student("axuebin",25,"FE"); console.log(me.say()); // axuebin:25 FE
|
apply
apply 也是属于所有 Function 的方法,也就是 Function.prototype.apply。
1
| fun.apply(thisArg, [argsArray])
|
和 call 用法一样,只是参数不同,call 的参数是列表,将每个参数都列出来;apply 的参数是数组,将每个参数放到一个数组中
完整的 apply
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| Function.prototype.myApply=function(context){ // 获取调用`myApply`的函数本身,用this获取,如果context不存在,则为window var context = context || window; var fn = Symbol(); context[fn] = this; //获取传入的数组参数 var args = arguments[1]; if (args == undefined) { //没有传入参数直接执行 // 执行这个函数 context[fn]() } else { // 执行这个函数 context[fn](...args); } // 从上下文中删除函数引用 delete context.fn; }
|
bind
bind()方法创建一个新的函数,当被调用时,将其 this 关键字设置为提供的值,在调用新函数时,在任何提供之前提供一个给定的参数序列。
1 2
| fun.bind(thisArg[, arg1[, arg2[, ...]]])
|
例子:
1 2 3 4 5 6 7 8 9 10
| function Person(name){ this.name = name; this.say = function(){ setTimeout(function(){ console.log("hello " + this.name); }.bind(this),1000) } } var person = new Person("axuebin"); person.say(); //hello axuebin
|
总结
- 三者都是用来改变函数的 this 指向
- 三者的第一个参数都是 this 指向的对象
- bind 是返回一个绑定函数可稍后执行,call、apply 是立即调用
- 三者都可以给定参数传递
- call 给定参数需要将参数全部列出,apply 给定参数数组