bind()
API
bind() 创建一个新的函数,新函数中的 this 绑定为 bind() 的第一个参数,其余参数作为新函数的参数;供之后调用使用。
function foo(b) {
console.log(this.a + b)
}
var obj = {
a: 0
}
// 创建了一个新函数
var bar = foo.bind(obj, 1)
// 再进行调用
bar() // 1如果使用 new 构造调用 bar ,那么 bind 绑定是无效的:
function foo() {
console.log(this.a)
}
var obj = {
a: 0
}
var a = 'oops, global'
// 无效绑定
var bar = foo.bind(obj)
// 使用 new 调用
new bar() // undefined, 注意不是绑定到了全局,而是绑定到一个新的空对象上了虽然使用
new调用会忽略this,但是后续传入的参数,在new调用时会被正确传入
实现细节
bind() 函数会创建一个新的绑定函数,它包装了原始函数;绑定函数内部有如下几个属性:
[[BoundTargetFunction]] - 被包装的原始函数
[[BoundThis]] -
this绑定的对象[[BoundArgumengts]] - 传入的剩余参数
调用绑定函数时,会调用 [[BoundTargetFunction]] 上的内部方法 [[call]] ,就像:Call(boundThis, args)
应用
柯里化
利用 bind() 可以创建一些预设好参数的函数:
正如上文所提,这里传给
bind()的 thisArg 最好是一个 DMZ 对象,这样更加安全
配合 setTimeout
前文提到过,在没有 ES6 的箭头函数时,回调函数中的 this 容易泄漏到全局对象上。我们可以用 bind() 包装一个回调函数,从而指定这个回调函数中的 this:
手写实现 bind()
根据 bind() 实现的功能:
按照前面的例子,可以测试下:
Last updated