1手写call
Function.prototype.myCall = function (context) {
// 判断调用myCall的是否是函数
if (typeof this !== 'function') {
throw new Error('not function')
}
// 如果mycall()里为空就指向window
context = context || window
// this指向调用的mycall的函数
context.fn = this // 把它挂到需要指向的对象上
// 取下后面需要的参数
let arg = [...arguments].slice(1)
let result;
result = context.fn(...arg) // 执行
delete context.fn // 用完删掉
return result
}
2手写apply
Function.prototype.myApply = function (context) {
if (typeof this !== 'function') {
throw new Error('not function')
}
context = context || window
// 向context添加一个属性,挂载this,this就是调用myApply的函数
context.fn = this
// 因为传入的参数是个数组,需要以这种形式解构,使得arg为一层数组
let [arg] = [...arguments].slice(1)
let result;
// 如果不携带参数,解构出来的arg为undefined,所以需要判断,而myCall中不带参数arg是个空数组,不需要判断
if (arg) {
result = context.fn(...arg)
} else {
result = context.fn()
}
delete context.fn
return result
}
3手写bind