//V1
Function.prototype.bind2 = function () {
const args = Array.from(arguments)
const obj = args.shift()
return () => this.apply(obj, args.concat(Array.from(arguments)))
}
// !!!!
// 完全错误 ,谨记箭头函数没有arguments和constructor
// V2
Function.prototype.bind2 = function () {
const args = Array.from(arguments)
const obj = args.shift()
const self = this
return function () {
self.apply(obj, args.concat(Array.from(arguments)))
}
}
// 还是有问题,bind之后的函数可以被当做构造函数,构造函数this指向新实例
// function test(m,n){
// console.log(`m:${m}---n:${n}`)
// this.name=m
// this.age=n
// this.male=true
// console.log("log this.a",a)
// }
// test.prototype.friend="xxx"
//V3
Function.prototype.bind2 = function () {
const args = Array.from(arguments)
const obj = args.shift()
const self = this
//这里可以被new调用,该函数prototype应该指向原函数
const fn = function () {
return self.apply(
this instanceof fn ? this : obj,
args.concat(Array.from(arguments))
)
}
// 这里还是有问题 修改fn的原型,原来的原型也会受影响
fn.prototype = this.prototype
return fn
}
//V4
Function.prototype.bind2 = function () {
const args = Array.from(arguments)
const obj = args.shift()
const self = this
//这里可以被new调用,该函数prototype应该指向原函数
const fn = function () {
return self.apply(
this instanceof fn ? this : obj,
args.concat(Array.from(arguments))
)
}
// 这里可以优化为create
const fnNOP = function () {}
fnNOP.prototype = this.prototype
fn.prototype = new fnNOP()
return fn
}
function MockCreate(proto) {
function F() {}
F.prototype = proto
return new F()
}
// V5
Function.prototype.bind2 = function () {
const args = Array.from(arguments)
const obj = args.shift()
const self = this
const fn = function () {
return self.apply(
this instanceof fn ? this : obj,
args.concat(Array.from(arguments))
)
}
fn.prototype = Object.create(this.prototype)
return fn
}