1.代码
Function.prototype.before = function(beforefn) {
let _self = this;//记录原函数
return function(){
console.log(this);//
console.log(arguments);
beforefn.call(this,arguments);//修正this值
return _self.apply(this,arguments);
}
}
Function.prototype.after = function(afterfn) {
let _self = this;//
return function(){
console.log(this);//window
console.log(arguments);
let ret = _self.apply(this,arguments);//修正this值,并且执行原函数
afterfn.apply(this,arguments);
console.log(ret);
return ret;
}
}
let func = function(){
console.log(2);
}
let func2 = func.before(function(){console.log(1)}).after(function(){console.log(3)});
let obj = {f:func2};
func2();
obj.f();
2.输出结果
3.分析
func2 = func.before(function(){console.log(1)}).after(function(){console.log(3)});
最关键之处在于这一行代码,拆开来看
func.before(function(){console.log(1)})
func调用before方法,此时在 before方法体内this指向调用before方法的对象,也就是func然后返回了一个匿名函数,此时匿名函数体内_self指向最初的func方法。
再看.after(function(){console.log(3)})
匿名函数调用after方法,在after方法体内,this指向匿名函数,_self保存的是匿名函数,然后after方法返回的仍然是一个匿名函数。在这个匿名函数内_self指向before返回的匿名函数,ret是func的返回值。
然后将返回的匿名函数赋值给func2;
直接执行func2时,this指向全局,非严格模式下默认是window
当通过对象调用时,this指向调用函数的对象。