最新公告
  • 欢迎您光临起源地模板网,本站秉承服务宗旨 履行“站长”责任,销售只是起点 服务永无止境!立即加入钻石VIP
  • JS中的公有属性和私有属性

    正文概述 掘金(极致同学)   2020-12-15   516

    公有属性和私有属性指什么

    function constructor() {1
      var clure_v = "a"; // 闭包属性
      var clure_f = function () {
        // 私有方法
        // code
        console.log(clure_v);
      };
    
      this.private_v = "b"; // 私有属性
      // 私有方法
      this.private_f = function () {
        console.log(this.clure_v,clure_v);
        clure_v += "a";
        clure_f();
      };
    }
    constructor.prototype.public_v = "c";
    constructor.prototype.public_f = function () {
      console.log(this.clure_v, this.private_v, this.public_v);
    };
    console.log(constructor);
    let c1 = new constructor();
    console.log(c1);
    console.log(c1.clure_v); //undefined
    console.log(c1.private_v); //'b'
    console.log(c1.public_v); //'c'
    console.log(constructor.clure_v); //undefined
    console.log(constructor.private_v); //undefined
    console.log(constructor.public_v); //undefined
    c1.private_f();
    //undefined 'a'  'aa'
    c1.private_f();
    //undefined 'aa'  'aaa'
    c1.public_f(); //undefined "b" "c"
    console.log(c1.hasOwnProperty("clure_v")); //false
    console.log(c1.hasOwnProperty("private_v")); //true
    console.log(c1.hasOwnProperty("public_v")); //false
    console.log("clure_v" in c1); //false
    console.log("private_v" in c1); //true
    console.log("public_v" in c1); //true
    
    

    从上面的例子中我们可以得到

    1. JavaScript中的属性有内部定义不用this指向的属性,我们姑且称其为闭包属性,因为它对其属性起到一个保存和保护的作用,不会污染外部资源。in hasOwnProperty都不能检测到他,不能使用this访问,
    2. 另外有私有属性,就是在构造函数内部使用this指向定义的属性,该属性可以使用in hasOwnProperty检测来判断其是否是一个对象的属性
    3. 公有属性,及原型链上的属性,该属性可以通过this访问,可以使用in,检测出来,不能使用hasOwnProperty检测出来。

    检测name是对象obj的属性

    in 操作符

    特点是无论是私有属性还是公有属性,只要有,就会返回true

    hasOwnProperty

    特点是,只有检测对象是其私有属性时才会返回true,否则返回false

    JavaScript如何确定name是对象obj私有属性

    obj.hasOwnProperty('name')
    

    JavaScript如何确定name是对象obj公有属性

    function getPubProperty(obj, attr) {
      /*
      第一种方法 使用 in 和 hasOwnProperty 
      已知,in可以用来判断公有和私有属性,hasOwnProperty可以用来判断私有属性,那么如果一个属性用in判断返回true,用hasOwnProperty判断返回false,就说明这个属性是公有属性
      但是,需要注意的是:如果一个属性既是公有属性又是私有属性,判断就会出错
      */
      /**
       * 第二种方法,也是最正确的方法
       * 就是检测原型上的属性,因为原型链上的属性都是公有的
       */
      let proto = obj.prototype;
      while (proto) {
        if (proto.hasOwnProperty(attr)) {
          return true;
        }
        proto = proto.prototype;
      }
      return false;
    }
    
    console.log(getPubProperty(c1, "public_v")); //true
    console.log(getPubProperty(c1, "public_f")); //true
    console.log(getPubProperty(c1, "private_v")); //false
    

    对象遍历问题及解决方案

    我们通常所用的遍历方式是 (for ... in ...for ... of ...)

    for ... in ...

    for ... in ...循环的特点是

    1. 对象的私有属性和公有属性都会被遍历到
    2. 但是不会遍历到对象的symbol属性
    let sy = Symbol();
    let obj = {
      2: 2,
      1: 1,
      a: "a",
      b: "a",
      [sy]: "Symbol(sy)",
    };
    obj.c = "c";
    Object.prototype.publica = "publica";
    obj.d = "d";
    for (const key in obj) {
      console.log(key);
      // if (obj.hasOwnProperty(key)) {
      //   console.log(key);
      // }
      //在上面的控制下只会输出
    }
    /**
     * 1
     * 2
     * 'a'
     * 'b'
     * 'c'
     * 'd'
     * 'publica'
     */
    

    for ... of ...

    for ... of ...循环的特点是

    其循环对象必须要有具有Symbol.iterator属性,调用这个接口就会返回一个遍历器对象。

    原生部署了这个接口的数据结构如下

    1. Array
    2. Map
    3. Set
    4. String
    5. TypedArray
    6. 函数的arguments对象
    7. NodeList对象

    故而我们在使用for ... of ...循环遍历对象的时候,需要使用中间件将对象转化为具有Symbol.iterator接口的对象,这些中间件可以是如下几个:

    1. Object.keys(obj)

      返回一个数组,遍历对象私有属性,但是不遍历Symbol属性和公有属性

      console.log(Object.keys(obj));//["1", "2", "a", "b", "c", "d"]
      
    2. Object.values(obj)

      返回一个数组,里面是对象私有属性(不含Symbol属性)的值

      console.log(Object.values(obj));[1, 2, "a", "a", "c", "d"]
      
    3. Object.entries()

      返回一个二维数组,里面是对象私有属性(不含Symbol属性)的['键','值']

      console.log(Object.entries(obj));
      /*
      0: (2) ["1", 1]
      1: (2) ["2", 2]
      2: (2) ["a", "a"]
      3: (2) ["b", "a"]
      4: (2) ["c", "c"]
      5: (2) ["d", "d"]
      */
      
    4. Object.getOwnPropertyNames(obj)

      返回一个数组

      ["1", "2", "a", "b", "c", "d"]
      

      Object.keys(obj)结果相同

    5. Object.getOwnPropertySymbols(obj)

      返回一个数组,遍历对象Symbol私有属性

      [Symbol()]
      
    6. Reflect.ownKeys(obj)

      返回一个数组,遍历对象的包含Symbol属性的私有属性

      ["1", "2", "a", "b", "c", "d", Symbol()]
      

    上面这几种遍历器方法都会遵循以下几个规则

    1. 首先遍历所有属性名为数值的属性,按照数字排序
    2. 其次遍历所有属性名为字符串的属性,按照生成时间排序
    3. 最后遍历所有属性名为Symbol值的属性,按照生成时间排序
    4. 先遍历私有属性,再遍历公有属性

    起源地下载网 » JS中的公有属性和私有属性

    常见问题FAQ

    免费下载或者VIP会员专享资源能否直接商用?
    本站所有资源版权均属于原作者所有,这里所提供资源均只能用于参考学习用,请勿直接商用。若由于商用引起版权纠纷,一切责任均由使用者承担。更多说明请参考 VIP介绍。
    提示下载完但解压或打开不了?
    最常见的情况是下载不完整: 可对比下载完压缩包的与网盘上的容量,若小于网盘提示的容量则是这个原因。这是浏览器下载的bug,建议用百度网盘软件或迅雷下载。若排除这种情况,可在对应资源底部留言,或 联络我们.。
    找不到素材资源介绍文章里的示例图片?
    对于PPT,KEY,Mockups,APP,网页模版等类型的素材,文章内用于介绍的图片通常并不包含在对应可供下载素材包内。这些相关商业图片需另外购买,且本站不负责(也没有办法)找到出处。 同样地一些字体文件也是这种情况,但部分素材会在素材包内有一份字体下载链接清单。
    模板不会安装或需要功能定制以及二次开发?
    请QQ联系我们

    发表评论

    还没有评论,快来抢沙发吧!

    如需帝国cms功能定制以及二次开发请联系我们

    联系作者

    请选择支付方式

    ×
    迅虎支付宝
    迅虎微信
    支付宝当面付
    余额支付
    ×
    微信扫码支付 0 元