赞
踩
proxy: 代理
扩展(增强)对象、方法(函数)一些功能
比如:
Vue
Vue.config.keyCodes.enter=65
Proxy作用: 比如vue中拦截
预警、上报、扩展功能、统计、增强对象等等
proxy是设计模式一种, 代理模式
语法:
new Proxy(target, handler);
let obj = new Proxy(被代理的对象,对代理的对象做什么操作)
handler:
{
set(){}, //设置的时候干的事情
get(){}, //获取干的事情
deleteProperty(){}, //删除
has(){} //问你有没有这个东西 ‘xxx’ in obj
apply() //调用函数处理
.....
}
- let obj = {
- name:'Strive'
- };
-
- let newObj = new Proxy(obj,{//代理obj
- get(target, property){//property 属性 get是获取信息
- //console.log(target, property);
- //TODO
- console.log(`您访问了${property}属性`);
- return target[property];//没有return返回值会都出现undefined
- }
- });
-
- console.log(newObj.name);
实现一个,访问一个对象身上属性,默认不存在的时候给了undefined,希望如果不存在错误(警告)信息:
- let newObj = new Proxy(obj, {
- get(target, property){
- if(property in target){
- return target[property];
- }else{
- //throw new ReferenceError(`${property}属性不在此对象上`);
- console.warn(`${property}属性不在此对象上`);
- return '^_^';//替换了出现的undefined
- }
- }
- });
DOM.div()
DOM.a();
DOM.ul()
例:
- <script>
- const DOM = new Proxy({},{
- get(target, property){
- //console.log(target, property);
- //property就是DOM.xxx 里面的xxx
- return function(attr={}, ...children){//json的内容,其他内容
- //console.log(attr, children);
- const el = document.createElement(property);
-
- //添加属性
- for(let key of Object.keys(attr)){
- el.setAttribute(key, attr[key]);
- }
- //添加子元素
- for(let child of children){
- if(typeof child == 'string'){
- child = document.createTextNode(child);//创建文本节点
- }
- el.appendChild(child);//添加
- }
- return el;
- }
- }
- });
-
- let oDiv = DOM.div({id:'div1',class:'aaa'},'我是div','呵呵呵');//json,内容,……
-
- console.log(oDiv);
- </script>
- const DOM = new Proxy({},{
- get(target, property){
- //console.log(target, property);
- //property DOM.xxx 里面的xxx
- return function(attr={}, ...children){
- //console.log(attr, children);
- const el = document.createElement(property);
-
- //添加属性
- for(let key of Object.keys(attr)){
- el.setAttribute(key, attr[key]);
- }
- //添加子元素
- for(let child of children){
- if(typeof child == 'string'){
- child = document.createTextNode(child);
- }
- el.appendChild(child);
- }
- return el;
- }
- }
- });
-
- let oDiv = DOM.div(
- {id:'div1',class:'aaa'},'我是div','呵呵呵',
- DOM.a({href:'http://www.51mmr.net'}, '访问官网'),
- DOM.ul({},
- DOM.li({},'1111'),
- DOM.li({},'2222'),
- DOM.li({},'3333'),
- DOM.li({},'4444')
- )
- );
-
- window.onload=function(){
- document.body.appendChild(oDiv);
- };
set(), 设置,拦截:
设置一个年龄,保证是整数,且范围不能超过200
- let obj =new Proxy({},{
- set(target, prop, value){
- if(prop == 'age'){
- if(!Number.isInteger(value)){
- throw new TypeError(`年龄必须为整数`);
- }
- if(value>200){
- throw new RangeError('年龄超标了,必须小于200岁');
- }
- }
- target[prop]=value;
- }
- });
-
- obj.a=123;
- obj.name = 'Strive';
-
- console.log(obj);
-
- obj.age = 201;
deleteProperty(): 删除,拦截:
- let json = {
- a:1,
- b:2
- };
-
- let newJson = new Proxy(json, {
- deleteProperty(target, property){
- console.log(`您要删除${property}属性`);
- //TODO
- delete target[property];
- }
- });
-
- delete newJson.a;
-
- console.log(newJson);
has(): 检测有没有
- let newJson = new Proxy(json, {
- deleteProperty(target, property){
- console.log(`您要删除${property}属性`);
- //TODO
- delete target[property];
- },
- has(target, property){
- console.log(`判断是否存在调用has方法`);
- //TODO
- return property in target;
- }
- });
-
- console.log('a' in newJson);
apply(target,context指向,args参数数组) :拦截方法
- function fn(){
- return '我是函数';
- }
-
- let newFn = new Proxy(fn, {
- apply(){
- return '函数么?';
- }
- });
-
- console.log(newFn());
Reflect: 反射
将Object.xxx 语言内部方法如:Object.defineProperty放到Reflect对象身上
通过Reflect对象身上直接拿到语言内部东西
比如:
'assign' in Object -> Reflect.has(Object, 'assign')
delete json.a -> Reflect.deleteProperty(json, 'a');
- let json ={a:1, b:2};
-
- /* delete json.a;
- console.log(json); */
-
- Reflect.deleteProperty(json, 'a');
-
- console.log(json);
Reflect.apply(调用的函数,this指向,参数数组);与fn.call() fn.apply() 作用类似
- let res = Reflect.apply(Math.ceil,null, [9.8]);//变形式调用函数
-
- console.log(res);
- function show(...args){
- console.log(this);
- console.log(args);
- }
-
- //show(1,2,3,4);
-
- //show.call('abc', 1,2,3,4);将this改变成abc
- //show.apply('abcd',[1,2,3,4]);
-
- Reflect.apply(show, 'aaaa', [1,2,3,4]);
- function sum(a,b){
- return a+b;
- }
-
- let newSum = new Proxy(sum, {
- apply(target, context, args){
- //console.log(target, context, args);
- //console.log(...arguments);
- return Reflect.apply(...arguments);
- }
- });
-
- console.log(newSum(2,3))
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。