Home >Web Front-end >JS Tutorial >What is Proxy in ES6? Detailed analysis of Proxy

What is Proxy in ES6? Detailed analysis of Proxy

不言
不言Original
2018-09-27 16:21:393539browse

The content of this article is about what is Proxy in ES6? The detailed analysis of Proxy has certain reference value. Friends in need can refer to it. I hope it will be helpful to you.

proxy means proxy in Chinese. The word has similar meanings in other programming languages.

What is it

Proxy is a constructor. The typical feature of constructors in js is that the first letter is capitalized. We create objects in the new Proxy (original object, {proxy list}) format. The created object is called a proxy object.
That is:

Proxy object = new Proxy (original object, {proxy list})

The reason why such an additional proxy object is generated is that the original object can be kept unchanged. Add new functions to the proxy object, or modify certain functions. The original object can be rolled back at the appropriate time. It can be compared and understood with the agent pattern in design patterns.

Usage format

var obj;
var proxyObj = new Proxy(obj, {
    对obj的操作1: 函数1,
    对obj的操作2: 函数2,
    ...
    
})

Getting started example

Basic demonstration of Proxy

var obj = {name:'fan',age:34}
console.info(obj.name)

var proxyObj = new Proxy(obj,{
    get:function(target,key,receiver){console.info(target,key,receiver); return 'no'}
})

console.info(proxyObj.name) 
console.info(proxyObj.abc)

The explanation is as follows:

  • proxxy The object is a new object created based on the obj object.

  • proxyObj.name is to get the name attribute of the proxy object. .The operator will automatically call the get() method. This is very important. In js, an object is an unordered collection of properties. The object only has attributes, and nothing else. We often talk about calling a certain method of the object: for example, the sort method of the array object arr: arr.sort(). The sort here is also an attribute of the arr object (more rigorously) , sort is an attribute of the object arr.__proto__). Compared with the length attribute, the attribute value of the sort attribute is a function, so add () after it to execute this function, and the value of the length attribute is a numerical value. So you can use it directly without adding (). Let me emphasize again: the operation of the object will automatically call get. Of course, we don't realize this when we usually use it.

  • In the second parameter of new Proxy, the get method is clearly set: when accessing any attribute of proxyObj, the values ​​of target, key, and receiver are output, and no is returned uniformly. . So both proxyObj.name and proxyObj.abc will get no.

Writing this, what do you think is the relationship between the original object and the proxy object? Why is it called

Agent?

Understand the role of the agent

The agent object can be understood as the star’s agent.

外界 <----> 原对象;
外界 <----> 代理对象 <------> 原对象;
Let’s take the above code as an example to improve the requirements: if someone asks obj’s name, tell the person directly; if someone asks obj’s age, return the age 5 years younger.

var obj = {name:'fan',age:34}
console.info(obj.age)           // 34
var proxyObj = new Proxy(obj,{
    get:function(target,key,receiver){
        console.info(target === obj);           //true
        console.info(receiver === proxyObj);    //true
        if('age' === key){
            return target[key] - 5;
        }
        else{
            return target[key]
        }
    }
})

console.info(proxyObj.age)  // 34- 5 = 29
The explanation is as follows:

  • The three parameters in the get function: target, key, receiver. target is the original object j, keys is the current attribute name; receiver is the proxy object. You can do any custom processing in the get method.

The relationship between the proxy object and the original object

var arr = [2,1]
var proxyArr = new Proxy(arr,{} )
proxyArr.push(3);
console.info(arr) // [2,1,3]
console.info(arr === proxyArr) // false
arr.sort();
console.info(proxyArr[0]) // 1

In the above code, this proxy object does not perform any special operations. It is understood that the managers of celebrities are passive in their work: conveying the information from the outside world to the celebrities themselves. Therefore, operations performed on proxyArr will directly affect arr.

Similarly, operations on arr will also affect proxyArr.

But please note: proxyArr and arr are two different objects: arr !== proxyArr.

You may think about it: Why can proxyArr directly use the push method? The reason is:

proxyArr.__proto__ === arr.__proto__ === Array.prototype
The reason why the previous equation is true is determined by the gene of new Proxy: the original object is proxied.

Proxy list

In the second parameter of new Proxy, the proxy attributes that can be set are as follows:

var proxyObj = new Proxy(obj, {

    get: function(tagert,key,receiver){},
    set: function(tagert,key,receiver){},
    has: function(tagert,key){},
    deleteProperty: function(tagert,key){},
    ownKeys: function(tagert){},
    getOwnPropertyDescriptor: function(tagert,key){},
    defineProperty: function(tagert,key,desc){},
    preventExtensions: function(tagert){},
    getPrototypeOf: function(tagert){},
    isExtensible: function(tagert){},
    setPrototypeof: function(tagert,proto){},
    apply: function(tagert,obj,args){},
    construct: function(tagert,args){},
    
})
get() Application of proxy

Allow array subscripts to be negative values

In js, the valid array table starts from 0.

var arr = [1,2,3];
console.info(arr[0])  // 1
console.info(arr[-1]) // undefined
console.info(arr[100]) // undefined
It is worth noting that when the following table is out of bounds or has a negative value, the result obtained is undefined instead of an error.

Below we hope that the array can take negative values ​​as shown in the table below. The rules are as follows:

  • -n represents the nth element from the last. For example: -1 means the first element from the last.

Use Proxy to solve the problem as follows:

var arr = [1,2,3];

var proxyArr = new Proxy(arr,{
    get: (target,prop)=>{
        let index = Number(prop);
        if(index < 0){
            prop = target.length + index;
        }
        return target[prop];
        
    }
})
console.info(arr[-1]);      // undefined
console.info(proxyArr[-1]); // 3

Note:

  • Number() can convert the incoming value into a numerical value type. Non-numeric value --> NaN;

  • If it is proxyArr.push(3), since the prop at this time is 'push', it will not enter the if branch.

  • If it is proxyArr[-1], the prop at this time is '-1', so it will enter the if branch: change the prop from -1 to 2, thereby achieving the The effect of agency.

  • At this point, proxyArr can be used as an array, and methods such as sort and push can be called. Array.isArray(proxyArr) === true

  • Of course, you can also further encapsulate it into a factory function.

    function myArr(...args){
        var arr = new Array(...args);
    
        var proxyArr = new Proxy(arr,{
            get: (target,key)=>{
                let index = Number(key);
                if(index < 0){
                    key = target.length + index;
                }
                return target[key];
    
            }
        })
        return proxyArr;
    }
    var obj = myArr([1,2,3]);
    console.info(obj[0],obj[-1])

    Chain operation

    var double = n => n*2;
    var pow2 = n => n*n;
    var half = n => n/ 2;
    var add1 = n => n+1;
    
    function pipe (num){
        let funs = []
        let obj = new Proxy({},{
            get:function(target,prop){
                if(prop === 'end'){
                    return funs.reduce((val,currentfn)=>currentfn(val),num);
                }else{
                    funs.push(window[prop])
                }
                return obj;
            }
        })
    
        return obj;
    };
    
    console.info( pipe(4).double.pow2.end);
    console.info( pipe(4).pow.double.pow2.add1.end);

    The above is the detailed content of What is Proxy in ES6? Detailed analysis of Proxy. For more information, please follow other related articles on the PHP Chinese website!

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn