Proxy(一)

Proxy
proxy接受一个待代理目标对象和一些包含元操作的对象,为待代理目标创建一个‘屏障’,并拦截所有操作,重定向到自定义的元操作对象上。

proxy通过new Proxy来创建,接受两个参数:
1、待代理目标对象
2、元操作对象

最简单的只代理一个方功能,在这个例子里,我们让get操作,永远返回一个固定的值

let target = {
  name: 'fox',
  age: 23
}
let handler = {
  get: (obj, k) => 233
}
target = new Proxy(target, handler);
target.a // 233
target.b // 233
target.c // 233

无论你taget.x、target[x]、Reflect.get(target, ‘x’)都会返回233 当然,代理get仅仅是其中一种操作,还有: - get - set - has - apply - construct - ownKeys - deleteProperty - defineProperty - isExtensible - preventExtensions - getPrototypeOf - setPrototypeOf - getOwnPropertyDescriptor

改变默认值为0

在其他语言中,如果访问对象中没有的属性,默认会返回0,这在某些场景下很有用,很方便,比如坐标系,一般来说z轴默认是0. 但是在js中,对象中不存在的key的默认值是undefined,而不是合法的初始值。 不过可以使用proxy解决这个问题

const defaultValueObj = (target, defaultValue) => new Proxy(target, {
  get: (obj, k) => Reflect.has(obj, k) ? obj[k] : defaultValue
})

建议根据不同类型返回不同的默认值,Number => 0 String => ‘’ Object => {} Array => []等等

数组负索引取值

js中,获取数组的最后一个元素是相对麻烦的,容易出错的。这就是为什么TC39提案定义一个方便的属性,Array.lastItem去获取最后一个元素。 其他语言比如python,和ruby提供了访问数组最后一个元素的方法,例如使用arr[-1]代替arr[arr.length - 1] 不过,我们有proxy,负索引在js中也可以实现。

const negativeArray = els => new Proxy(els, {
  get: (target, k) => Reflect.get(target, +k < 0 ? String(target.length + +k) : k)
})

需要注意的一点是,get操作会字符串化所有的操作,所以我们需要转换成number在进行操作, 这个运用也是negative-array的原理

隐藏属性

js未能实现私有属性,尽管之后引入了Symbol去设置独一无二的属性,但是这个被后来的Object.getOwnPropertySumbols淡化了 长期以来,人们使用下划线_来表示属性的私有,这意味着不运行外部操作该属性。不过,proxy提供了一种更好的方法来实现类似的私有属性

const enablePrivate = (target, prefix = '_') => new Proxy(target, {
  has: (obj, k) => (!k.startsWith(prefix) && k in obj),
  ownKeys: (obj, k) => Reflece.ownKeys(obj).filter(k => (typeof k !== 'string' || !k.startsWith(prefix))),
  get: (obj, k, rec) => (k in rec) ? obj[k] : undefined
})

结果

let userData = enablePrivate({
  firstName: 'Tom',
  mediumHandle: '@tbarrasso',
  _favoriteRapper: 'Drake'
})

userData._favoriteRapper        // undefined
('_favoriteRapper' in userData) // false
Object.keys(userData)           // ['firstName', 'mediumHandle']

如果你打印该proxy代理对象,会在控制台看到,不过无所谓。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值