简单Proxy使用
文章目录
- 前言
- 概念
前言
在完成仿写任务时,用其来检测变量的改变,故借此总结学习一下
概念
Proxy 可以拦截并自定义对某个对象的基本操作
语法如下
const name = new Proxy(target, handler);
target
:要被代理的对象
handler
:拦截器对象,里面放有“陷阱函数”
通过
name
访问target
时若此次操作行为在拦截器对象中存在对应的陷阱函数,那么此次操作将根据拦截器中对应的函数来触发
通过target直接访问原对象则不会触发
如下可以拦截数组的增加和删除功能
const arr=[1,2,3,4,5,6,7,8]const role=new Proxy(arr,{set(target, property, value){//对于数组操作 改值和改length都会触发,但我们的自定义方法仅需调用一次故console.log('在外部故触发俩次');if (property === 'length') {//只有当改length时才触发console.log('准备修改length');}let a=Reflect.set(target, property, value)//此方法就是进行此次操作赋值类似target[property]=value//返回值是是否成功完成此次赋值 成功为true反之//在此之后赋值已经完成了// 直到return a//陷阱函数也需要返回布尔值来确认此次方法是否成功},deleteProperty(target, property){//此方法只会在调用delete关键字才会触发console.log('准备删除');let result=Reflect.deleteProperty(...arguments);}})console.log(arr.length);delete role[2]//触发自定义的删除,但delete只是释放了对应的地址// 还需要role.push(9)console.log(arr.length);arr.splice(2,1)//来删除console.log(arr.length);console.log(arr);
控制台如图
陷阱函数
-
set
上述的set只拦截 赋值 操作
故role.push(9)
有俩次拦截,第一次是对数组扩充赋值的拦截
第二次则是给length赋予新值而被拦截 -
deleteProperty
deleteProperty只拦截删除操作
如上 -
get
拦截读取操作
//加入
,get(target, property){console.log('拦截读取');Reflect.get(...arguments);}
//调用
console.log(role[2])
结果
总结
- 陷阱函数需要返回布尔值来判断此次操作是否成功
可以调用Reflect.对应函数(...arguments)
来进行赋值
在此之前操作属于拦截状态未执行,反之 - set拦截的是赋值操作,对数组进行赋值会有俩次拦截
分别是length
赋值和扩充数组
- 使用