Proxy --概述篇

 概述:

  Proxy 用于修改某些操作的默认行为,等同于在语言层面做出修改,所以属于一种“元编程”(meta programming),即对编程语言进行编程。

  Proxy 可以理解成,在目标对象之前架设一层“拦截”,外界对该对象的访问,都必须先通过这层拦截,因此提供了一种机制,可以对外界的访问进行过滤和改写。Proxy 这个词的原意是代理,用在这里表示由它来“代理”某些操作,可以译为“代理器”。

var obj = new Proxy({}, {
  get: function (target, key, receiver) {
    console.log(`getting ${key}!`);
    return Reflect.get(target, key, receiver);
  },
  set: function (target, key, value, receiver) {
    console.log(`setting ${key}!`);
    return Reflect.set(target, key, value, receiver);
  }
});

  上面代码对一个空对象架设了一层拦截,重定义了属性的读取(get)和设置(set)行为。这里暂时先不解释具体的语法,只看运行结果。对设置了拦截行为的对象obj,去读写它的属性,就会得到下面的结果。

obj.count = 1
//  setting count!
++obj.count
//  getting count!
//  setting count!
//  2

  上面代码说明,Proxy 实际上重载(overload)了点运算符,即用自己的定义覆盖了语言的原始定义。

  ES6 原生提供 Proxy 构造函数,用来生成 Proxy 实例。

var proxy = new Proxy(target, handler);

  

  Proxy 对象的所有用法,都是上面这种形式,不同的只是handler参数的写法。其中,new Proxy()表示生成一个Proxy实例,target参数表示所要拦截的目标对象,handler参数也是一个对象,用来定制拦截行为。

  下面是另一个拦截读取属性行为的例子。

var proxy = new Proxy({}, {
  get: function(target, property) {
    return 35;
  }
});

proxy.time // 35
proxy.name // 35
proxy.title // 35

  上面代码中,作为构造函数,Proxy接受两个参数。第一个参数是所要代理的目标对象(上例是一个空对象),即如果没有Proxy的介入,操作原来要访问的就是这个对象;第二个参数是一个配置对象,对于每一个被代理的操作,需要提供一个对应的处理函数,该函数将拦截对应的操作。比如,上面代码中,配置对象有一个get方法,用来拦截对目标对象属性的访问请求。get方法的两个参数分别是目标对象和所要访问的属性。可以看到,由于拦截函数总是返回35,所以访问任何属性都得到35

  

  注意,要使得Proxy起作用,必须针对Proxy实例(上例是proxy对象)进行操作,而不是针对目标对象(上例是空对象)进行操作。

  如果handler没有设置任何拦截,那就等同于直接通向原对象。

var target = {};
var handler = {};
var proxy = new Proxy(target, handler);
proxy.a = ‘b‘;
target.a // "b"

  上面代码中,handler是一个空对象,没有任何拦截效果,访问proxy就等同于访问target

  一个技巧是将 Proxy 对象,设置到object.proxy属性,从而可以在object对象上调用。

var object = { proxy: new Proxy(target, handler) };

 

  Proxy 实例也可以作为其他对象的原型对象。

var proxy = new Proxy({}, {
  get: function(target, property) {
    return 35;
  }
});

let obj = Object.create(proxy);
obj.time // 35

  上面代码中,proxy对象是obj对象的原型,obj对象本身并没有time属性,所以根据原型链,会在proxy对象上读取该属性,导致被拦截。

  同一个拦截器函数,可以设置拦截多个操作。

var handler = {
  get: function(target, name) {
    if (name === ‘prototype‘) {
      return Object.prototype;
    }
    return ‘Hello, ‘ + name;
  },

  apply: function(target, thisBinding, args) {
    return args[0];
  },

  construct: function(target, args) {
    return {value: args[1]};
  }
};

var fproxy = new Proxy(function(x, y) {
  return x + y;
}, handler);

fproxy(1, 2) // 1
new fproxy(1,2) // {value: 2}
fproxy.prototype === Object.prototype // true
fproxy.foo // "Hello, foo"

转自: ECMAScript 6 入门

作者:阮一峰

时间: 2024-10-12 08:35:09

Proxy --概述篇的相关文章

Android核心分析 ----- Android电话系统-概述篇

Android电话系统之概述篇 首先抛开Android的一切概念来研究一下电话系统的最基本的描述.我们的手机首先用来打电话的,随后是需要一个电话本,随后是PIM,随后是网络应用,随后是云计算,随后是想我们的手机无所不能,替代PC.但是作为一个电话的基本功能如下: 0)拨叫电话,接听电话,挂断电话,发送短信,网络连接,PIM管理 1)由于电话运营商为我们提供了呼叫等待,电话会议等补充业务,所以我们的手机需要管理多路通话,如何管理? 2)来电时,我们要播出来电铃声,接通时我们需要切换语音通道,这个又

Java架构师成长之道之计算机组成原理概述篇

Java架构师成长之道之计算机组成原理概述篇 Java架构师成长之道 1.1 计算机的发展简史 1.1.1 计算机发展的四个阶段 自从1945年至今,计算机经历了电子管计算机,晶体管计算机,集成电路计算机以及超大规模集成电路计算机. 电子管计算机(1945年-1957年) 第二次世界大战是电子管计算机产生的催化剂,而最著名的电子管计算机是来自美国的埃尼阿克(ENIAC),这一时期的计算机有如下特点: 集成度小,占用空间大 功耗高,运行速度慢 操作复杂,更换程序需要接线 晶体管计算机(1957年-

掌上快递 APP 项目之概述篇

概述 学习Android开发也有一段时间了,利用业余时间独立制作的一款快递类APP软件.大概2个多星期吧,自己将其定位为"集快递信息追踪.附近快递点查询. 快递公司投诉功能为一体的便民生活类快递 app".难度不是非常大,主要是是能够锻炼一下自己近来所学的,这个小项目涉及到前端到后台.从数据模型到网络数据解析,还有百度map,为了使側滑效果好看还使用了slidingmenu_library开源库. 主要实现了下面功能: [1]输入快递单号或者扫描二维码 查询快递信息 [2]收藏当前快递

基于ONOS的SDN-IP架构概述篇

编者按:SDN-IP是ONOS上的一个应用程序,允许软件定义网络使用标准的边界网关协议(BGP)连接到外部网络.从BGP角度看,SDN网络表现为单一的自治系统(AS),其行为与任何传统的AS一样.基于AS的SDN-IP应用提供BGP和ONOS之间的集成整合机制,在协议层SDN-IP的行为作为一个有规则的BGP发言人.从ONOS的角度来看,它只是使用其服务,在SDN数据平面安装和更新相应的转发状态的应用程序. 1 架构目标  1.1 SDN-IP设计目标 (1)兼容性Compatibility:S

敏捷开发 之 理论概述篇

一. 敏捷实践 1. 敏捷宣言 个体与交互 胜过 过程和工具 可以工作的软件 胜过 面面俱到的文档 客户合作   胜过 合同谈判 响应变化   胜过 遵循计划 1.1 个体与交互胜过过程和工具 合作.沟通以及交互能力要比单纯的编程能力更为重要. 工具要选用合适的,不要一开始就盲目选择所谓强大的.要从小工具开始尝试,直到无法适用再去更换. 1.2 可以工作的软件胜过面面俱到的文档 面面俱到的文档需要花费大量的时间成本来编写和维护.过时的文档比没有文档更具危害性. Martin文档第一定律:直到迫切

【AR实验室】ARToolKit之概述篇

0x00 - 前言 我从去年就开始对AR(Augmented Reality)技术比较关注,但是去年AR行业一直处于偶尔发声的状态,丝毫没有其"异姓同名"的兄弟VR(Virtual Reality)火爆.至于MR(Mixed Reality)更像是Google Glass事情之后对AR的洗白.但是今年AR行业出了件大事,没错,别左右看了,说的就是你 —— Pokemon GO.暂且不讨论这款游戏是不是AR游戏,毕竟争议挺大,但是这款游戏着实是让AR火了一把.AR应用开发貌似也有了燎原之

Ceph企业分布式存储——概述篇

一.概述 Ceph是可靠的.可扩展的.统一的.开源分布式的存储系统.可以同时提供对象存RADOSGW(Reliable.Autonomic.Distributed.Object Storage Gateway).块存储RBD(Rados Block Device).文件系统存储Ceph FS(Ceph Filesystem)3种功能. Ceph是一个开源的分布式文件系统.因为它还支持块存储.对象存储,所以很自然的被用做云计算框架openstack或cloudstack整个存储后端.当然也可以单独

WPF学习笔记之-WPF概述篇(两大亮点)

WPF的两大亮点 一.硬件加速 WPF 图形显示是基于DirectX(最初是为游戏显示开发的图形显示引擎),而非GDI/GDI+. WPF的目标是将尽可能多的工作交给显卡处理,所以复杂图形通常属于渲染范围(由GPU处理)而不属于处理器范围(由计算机的CPU处理).也就是说,可以让CPU空闲下来去完成其他工作,充分利用显卡的功能,并且还可以充分利用未来新显卡所具备的不断增加的新功能. WPF渲染级别(WPF TIERS) 显卡功能的区别是非常重要的.当WPF访问显卡时,它会考虑许多因素,包括显卡上

内核编译图文教程,概述篇

内核编译的主要任务就是把自己的硬件对应的编译进内核或模块. 尽量去掉内核中自己没有的硬件. 所以用一些探测自己硬件的命令非常重要. 比如自己的显卡,键盘鼠标,硬盘,网卡声卡. 现在(2015年)的机器基本上 显卡是n卡或a卡, 键盘鼠标一般是usb的, 硬盘一般是sata的,原来的是ide的.可以用df命令查看. 文件系统一般是ext4,原来的是ext3,可以用blkid命令查看. 因为家庭一般都在用无线路由,网卡一般都是接usb无线网卡啦,所以pppoe协议也不用编译啦. 我们一般在官方发布版