js基础知识(公有方法、私有方法、特权方法)

  1. 公有方法:公有方法就是能被外部访问并调用的方法。

    • 可以理解为创建了一个类Rest,里面的静态的方法

      //这样的定义相当于**静态的,直接可以通过Rest**,访问
      var Rest = {
       name: 'rest',
       // 公有方法
       getName: function() {
       return this.name;
       }
      }
      console.log(Rest.getName());//rest
    • 创建类,然后通过对象来调用方法

      // 在构造函数中
      function Person(name, age) {
       this.name = name;
       this.age = age;
       // 公有方法
       this.getName = function() {
       return this.name;
       }
      }
      // 在原型中
      Person.prototype.getAge = function() {
       return this.age;
      }
      var person = new Person("wangji",12);
      console.log(person.getName());//wangji
      console.log(person.getAge());//12
  2. 私有方法和特权方法
    这两个方法一般放在一起讨论,原因在于我们定义的特权方法是指有权访问内部私有属性和私有方法的公有方法(能够访问私有方法,私有属性的方法叫特权方法,也是公有方法的一种),而私有方法是指外部不可见且不可访问的方法。
    通常定义一个对象的方式有二种
    一是使用Object实例化或者对象表达式
    二是使用构造函数。
    同样在不同的方式下面定义私有方法和特权方法的形式也不相同

    在对象中

    这里我们通过Object对象表达式来创建一个对象并添加一些属性和方法,然后直接采用静态的方式调用。如Rest.getName();

    立即执行函数:对象的私有数据放置在一个匿名函数立即执行表达式(IIFE)中,这意味着这个函数只存在于被调用的瞬间,一旦执行后就立即被销毁了。

    在对象中创建私有数据的方式在对象的模式(指创建对象的模式)中被称之为模块模式,可以直接通过静态的调用,返回的是相当于一个{}对象,可以直接调用。

    var yourObject = (function() {
    
     // 私有属性和方法
     return {
     // 公有方法和属性
     }
    }) ();
    
    这里和前面的定义Rest一样啊,可以通过yourObject直接的访问。这样的模块化的访问还是比较的厉害的。

    例子

     var TaoBao = (function() {
     // 私有属性
     var _total = 10;
    
     // 私有方法
     var _buyFood = function() {
         _total--;
     }; 
     var _getTotal = function() {
        return _total;
     }
    
     return {
        name: 'taobao',
        getTotal: _getTotal,//使用了闭包的方式来间接使用内部私有变量
        buy: _buyFood
     }
    }) ();
    
    TaoBao.buy();
    console.log(TaoBao.name); // 'taobao'
    console.log(TaoBao.getTotal()); // 9

    使用了闭包的方式来间接使用内部私有变量

    在构造函数中

    在上面介绍的模块模式创建私有方法时,公有方法和特权方法并没有什么本质上的区别,原因在于这个概念是来自于使用构造函数创建私有数据的时候定义出来的。
    在构造函数中定义私有属性和方法很方便,我们不需要使用闭包,可以在调用的时候初始化数据

    function TaoBao(name) {
     // 私有属性
     var _total = 10;
    
     // 公有属性
     this.name = name;
    
     // 私有方法
     function _buyFood() {
        _total--;
     }
    
     // 特权方法,才能访问私有的属性和私有的方法
     this.buy = function() {
         _buyFood();
     }
    
     this.getTotal = function() {
        return _total;
     }
    }
    
    // 公有方法, 注意这里不能访问私有成员_total
    TaoBao.prototype.getName = function() {
        //console.log(_total); // Uncaught ReferenceError: _total is not defined
        return this.name;
    }
    
    var taobao = new TaoBao('taobao');
    console.log(taobao.getName()); // 'taobao'
    taobao.buy();
    console.log(taobao.getTotal()); // 9

    合二为一,更加灵活的方式
    使用模块模式我们可以多次调用,每次执行完后都会被销毁掉。
    使用构造函数方式可以传入一些初始化的数据,但在公有方法中无法访问到私有成员属性,如果有很多公有方法需要访问私有数据,我们全部用特权方法来写,最后会给每个实例带去很多没有必要的方法。
    因此,将两者结合在一起可以长短互补,结合方式也很简单

     var TaoBao = (function() {
     // 私有属性
     var _total = 10;
    
     // 私有方法
     function _buyFood() {
     _total--;
     }
    
     // 构造函数
     function TaoBao(name) {
     this.name = name;
     this.getTotal = function() {
     return _total;
     }
     }
     //这里怎么可以访问私有的方法??这里不是TaoBao内部的私有哦!
     TaoBao.prototype.buy = function() {
        console.log(_total); // 10
        _buyFood();
     }
    
     TaoBao.prototype.getName = function() {
        return this.name;
     }
    
     return TaoBao;
    }) ();
    
    var taobao = new TaoBao('taobao');
    console.log(taobao.getName()); // 'taobao'
    taobao.buy();
    console.log(taobao.getTotal()); // 9

    厉害了,get….