js手写实现call、apply、bind

const obj = { a: 1};
const func = function(val1,val2,val3) {
	console.log(this);
	console.log(val1, val2, val3);
}

func.call(obj, 1, 2, 3);

> 相当于obj={
> 				a: 1,
> 				func: function() {}
> 			}

func.apply(obj, [1, 2, 3]);

const newFunc = func.bind(obj, 1, 2, 3);
newFunc();

实现
func.myCall(obj, 1, 2, 3);
func.myApply(obj, [1, 2, 3]);
func.myBind(obj, 1, 2, 3);

Function.prototype.myCall = function(context, ...args) {
	args = args || [];
	const key = Symbol();// 生成唯一值,以防原对象中有重名
	context[key] = this; // context[key] = func, this指向调用方法的对象,也就是func
	const result = context[key](...args);
	delete context[key];
	return result;
}
Function.prototype.myApply = function(context, args) {
	args = args || [];
	const key = Symbol();
	context[key] = this;
	const result = context[key](...args);
	delete context[key];
	return result;
}
Function.prototype.myBind = function() {
	const args = Array.prototype.slice.call(arguments);
	const context = args.shift();
	const self = this;
	return function() {
		return self.apply(context, args);
	}
}

Function.prototype.myCall(context) {
	context = context || window;
	context.fn = this;
	let args = [...arguments].splice(1);
	let result = context.fn(...args);
	delete context.fn;
	return result;
}
Function.prototype.myApply(context) {
	context = context || window;
	context.fn = this;
	let result;
	if (arguments[1]) {
		result = context.fn(...arguments[1]);
	} else {
		result = context.fn();
	}
	delete context.fn;
	return result;
}
Function.prototype.myBind = function(context, ...args) {
	return (...innerArgs) => {
		let finalArgs = [...args, ...innerArgs];
		return this.apply(context, finalArgs);
	}
}
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值