对,所以我们在这里有三种调用函数的方式。它们都是解决上下文问题的方法,即this
关键字将根据函数的调用方式具有不同的值。
别名
var self = this;
setTimeout(function(){
console.log(self);
}, 5000);
这是一个非常简单的方法。它只是设置一个不会在函数中被覆盖的新变量。该值已关闭,因此在超时后调用该函数时,self
将是您所期望的。
捆绑
setTimeout($.proxy(function(){
console.log(this);
}, this), 5000);
setTimeout((function(){
console.log(this);
}).bind(this), 5000);
这两个函数具有相同的结果。这是因为$.proxy
与bind
. bind
但是,它是一种新语法,一些旧浏览器不支持。
这是通过将上下文永久“绑定”到函数来实现的。这意味着,无论函数如何调用, 的值this
始终是 的第一个参数的值bind
。
call
/apply
setTimeout((function(){
console.log(this);
}).call(this), 5000);
setTimeout((function(){
console.log(this);
}).apply(this), 5000);
同样,这两个功能是相同的。call
和之间的唯一区别apply
是发送给函数的其他参数。call
需要一个列表(例如fn.call(context, param1, param2)
),而apply
需要一个数组(fn.apply(context, [param1, param2])
)。
这两个函数所做的就是调用指定特定上下文的函数。
但是,这些功能都不能满足您的需求。他们都在特定的上下文中立即调用该函数,而不是等待 5 秒钟。那是因为call
和apply
工作就像()
:代码立即执行。
结论
哪种方法更合适将取决于您的任务。对于简单的操作,别名可能会很好地完成这项工作。但值得记住的是,这引入了另一个变量,并且不能在调用时设置上下文。其他方法在不同情况下也有其优势,特别是在编写用户提供回调函数的库时。