var jane = {
name: 'Jane',
sayHelloTo: function (otherName) {
'use strict';
console.log(this.name+' says hello to '+otherName);
}
};
第一个参数将被指向被调用函数的this值,其它的参数讲是调用函数所需要用到的。
下面三种调用所得到的结果是一样的
jane.sayHelloTo('Tarzan');
jane.sayHelloTo.call(jane, 'Tarzan');
var func = jane.sayHelloTo;
func.call(jane, 'Tarzan');
对于第二种方法,还需要把jane传入,因为call()并不知道你调用的是哪个对象。
其实,apply()与call()总体是一样的,只不apply()的第二个参数是以数组的形式传入。
jane.sayHelloTo('Tarzan');
jane.sayHelloTo.apply(jane, ['Tarzan']);
var func = jane.sayHelloTo;
func.apply(jane, ['Tarzan']);
通过调用bind()方法,产生了一个新的函数,thisValue将赋值给新函数的this,参数从arg1到argN。
function func() {
console.log('this: '+this);
console.log('arguments: '+Array.prototype.slice.call(arguments));
}
var bound = func.bind('abc', 1, 2);
> bound(3)
this: abc
arguments: 1,2,3
下面三种方法调用产生的结果是一样的。
jane.sayHelloTo('Tarzan');
var func1 = jane.sayHelloTo.bind(jane);
func1('Tarzan');
var func2 = jane.sayHelloTo.bind(jane, 'Tarzan');
func2();
可以看出,call()和apply()调用之后,立即执行了, 调用bind()并没有立即执行,因为调用它产生了一个新的函数,得去调用这个新的函数,才能执行。
现在有一个数组,选出数组中最大的值。
var array = [10,5,6,12];
当然,有很多方法可以实现。
现在通过Math.max()实现,下面的用法肯定很熟悉啦。
> Math.max(10,5,6,12)
12
对于函数而言,我们可以通过apply达到上面的效果。
> Math.max.apply(null,array)
12
apply仅仅在对函数或方法调用有作用
这里以new Date()为例
第一步:
给Data传递参数
new (Date.bind(null,2015,9.17))
第二步:
因为bind()是一个方法,所以我们可以对它apply().使用apply()给bind()传递一个数组。
new (Function.prototype.bind.apply(
Date, [null, 2011, 11, 24]))
稍作修改:
var arr = [2011, 11, 24];
new (Function.prototype.bind.apply(
Date, [null].concat(arr)))
做个简单的封装:
if (!Function.prototype.construct) {
Function.prototype.construct = function(argArray) {
if (! Array.isArray(argArray)) {
throw new TypeError("Argument must be an array");
}
var constr = this;
var nullaryFunc = Function.prototype.bind.apply(
constr, [null].concat(argArray));
return new nullaryFunc();
};
}
用法:
> Date.construct([2015,9,17])
Sat Oct 17 2015 00:00:00 GMT+0800 (中国标准时间)
何谓抽离一个方法?就是将一个对象中的某个方法单独提取出来赋值给一个变量,这个变量又是一个函数了。
比如:
var counter = {
count: 0,
inc: function () {
this.count++;
}
}
将inc提取出来:
> var func = counter.inc;
> func() //undefined
> counter.inc // didn’t work
0
这是为什么呢?
在执行counter.inc操作时,this已经指向了全局对象,相当于进行了window.count++操作。因为window.count不存在,那也就是undefined,对它进行++操作,得到的结果就是NaN了。
再严格模式下,它就会报错。
> counter.inc = function () { 'use strict'; this.count++ };
> var func2 = counter.inc;
> func2()
TypeError: Cannot read property 'count' of undefined
在严格模式下,this的值是undefined。
那就是运用bind()了。
> var func3 = counter.inc.bind(counter);
> func3()
> counter.count // it worked!
1