zoukankan      html  css  js  c++  java
  • JavaScript学习笔记-实例详解-类(二)

    实例详解-类(二)
     
    //===给Object.prototype添加只读不可枚举不可配置的属性objectId
    (function(){
    Object.defineProperty(Object.prototype,'objectId',{
    get:idGetter, //读取objectId时直接调用idGetter函数
    enumerable:false,
    configurable:false
    });
    function idGetter(){
    if(!(idprop in this)) { //检测是否存在idprop
    if (!Object.isExtensible(this)) {
    throw Error('can not define id for nonextensible objects');
    }
    Object.defineProperty(this, idprop, {
    value: nextid++,
    writable: false,
    enumerable: false,
    configurable: false
    });
    }
    return this(idprop);
    }
    var idprop = '|**objectid**|'; //假设这个属性没用到
    var nextid = 1;
    }());
    //====创建一个不可变得类,它的属性,方法都是不可变得===
    //===Object.defineProperty()和Object.defineProperties()可以用来创建新属性,也可以修改已有属性的特性。
    // 更改或设置属性描述时,未指定的属性保持已有值,默认是false
    function Range(from,to){
    var props = {
    from:{value:from,enumerable:true,writable:false,configurable:false},
    to:{value:to,enumerable:true,writable:false,configurable:false}
    };
    if(this instanceof Range) Object.defineProperties(this,props);
    else return Object.create(Range.prototype,props);
    }
    //添加不可变方法,除了value,其它都是false
    Object.defineProperties(Range.prototype,{
    includes:{value:function(x){return this.from<=x && x<=this.to;}},
    foreach:{value:function(f){for(var x=Math.ceil(this.from);x<=this.to;x++) f(x)}}
    });
    //=====设置属性描述的工具函数========
    function freezeProps(o){
    var props = (arguments.length == 1) //如果只有一个参数
    ?Object.getOwnPropertyNames(o) //使用所有属性
    :Array.prototype.slice.call(arguments,1); //否则传入了指定名字的属性
    props.forEach(function(n){
    //if(!Object.getOwnPropertyDescriptor(o,n).configurable) return; //忽略不可配置属性
    Object.defineProperty(o,n,{writable:false,configurable:false});
    });
    return o;
    }
    function hideProps(o){
    var props = (arguments.length == 1)
    ?Object.getOwnPropertyNames(o)
    :Array.prototype.slice.call(arguments,1);
    props.forEach(function(n){
    //if(!Object.getOwnPropertyDescriptor(o,n).configurable) return;
    Object.defineProperty(o,n,{enumerable:false});
    });
    return o;
    }
    //==使用以上工具函数
    function Range1(from,to){
    this.from = from;
    this.to = to;
    freezeProps(this);
    }
    Range1.prototype = hideProps({
    constructor:Range1,
    includes:function(x){return this.from<=x && x<= this.to;},
    foreach:function(f){for(var x=Math.ceil(this.from);x<=this.to;x++) f(x)},
    toString:function(){return '('+this.from+'...'+this.to+')'}
    });
    var r = new Range1(4,6);
    r.from = 1;
    r.to = 8;
    console.log(r.from); //4 无法修改
    console.log(r.to);
    //==========封装对象的私有状态(构造函数的属性)======
    function Range2(from,to){
    function getFrom(){return from;}
    function getTo(){return to;}
    function setFrom(f){ from = f;}
    function setTo(t){ to = t;}
    Object.defineProperties(this,{
    from:{get:getFrom,set:setFrom,enumerable:true,configurable:false},
    to:{get:getTo,set:setTo,enumerable:true,configurable:false}
    });
    }
    Range2.prototype = hideProps({
    constructor:Range1,
    includes:function(x){return this.from<=x && x<= this.to;},
    foreach:function(f){for(var x=Math.ceil(this.from);x<=this.to;x++) f(x)},
    toString:function(){return '('+this.from+'...'+this.to+')'}
    });
  • 相关阅读:
    Luogu P3731 [HAOI2017]新型城市化
    Luogu P3227 [HNOI2013]切糕 最小割
    Luogu P1654 OSU!
    CF235B Let's Play Osu! 期望dp
    Luogu P2057 [SHOI2007]善意的投票
    任意模数NTT学习笔记
    Burnside引理的感性证明
    JLOI2015 城池攻占
    BZOJ2957 楼房重建
    NOI2009 区间
  • 原文地址:https://www.cnblogs.com/susufufu/p/5705785.html
Copyright © 2011-2022 走看看