zoukankan      html  css  js  c++  java
  • Javascript 中创建自定义对象的方法(设计模式)

    Javascript 中创建对象,可以有很多种方法。

    Object构造函数/对象字面量:

    抛开设计模式不谈,使用最基本的方法,就是先调用Object构造函数创建一个对象,然后给对象添加属性.

    1     var student = new Object();
    2     student.name = "xiao ming";
    3     student.age = 20;
    4     student.getName = function () {
    5         alert(this.name);
    6     }

    熟悉javascript 对象字面量的同学,可以换一种更好的写法,至少看上去更简洁。

    1     var student = {
    2         name: "xiao hong",
    3         age: 18,
    4         getName: function () {
    5             alert(this.name);
    6         }
    7     };

     缺点:上面方法有个缺点就是,使用同一个接口创建很多类似的对象时,会产生大量重复的代码。这个应该很容易理解了,函数(方法或者类)一般是用来创建公共的方法,上面的对象创建过程,根本没有函数的影子,所以谈不上什么重用。

    工厂模式:

    工厂模式 抽象了具体创建对象的过程。就像一个黑盒,你只要调用函数(进入工厂),并且传入相应参数(各种原材料),就会出来一个相应的对象(工厂生产的产品)。工厂模式解决了创建多个相似对象的问题。

     1     function studentFactory(name,age) {
     2         var student = new Object();
     3         student.name = name;
     4         student.age = age;
     5         student.sayName = function () {
     6             alert(this.name);
     7         }
     8         return student;
     9     }
    10     var p1 = studentFactory("ming", 20);
    11     var p2 = studentFactory("hong", 18);

    缺点:工厂模式也有缺点,最大的缺点就是 对象类型识别的问题。只能判断出对象是Object 类型(p1 instanceof Object),而无法具体判断出来是哪种类型。使用工厂模式创建出来的student 其实都有着类似的属性和方法,只是值不同而已。这时 更好的解决方法是,创建一个Student 函数,这样所有的对象都属于 Student 类型。所以工厂模式不是不好,只是 构造函数模式更优。

    自定义类型的构造函数:

    构造函数可以用来创建特定类型的对象。

     1     function Student(name,age) {
     2         this.name = name;
     3         this.age = age;
     4         this.sayName = function () {
     5             alert(this.name);
     6         }
     7     }
     8     var p3 = new Student("ming", 20);
     9     var p4 = new Student("hong", 18);
    10     alert(p3 instanceof Student); 
        alert(p3.sayName==p4.sayName); //false

    缺点:自定义构造函数 的不足之处就是,每个对象都会重新创建自己的方法,其实这些方法功能是一样的(像 sayName),但是它们却不相同(p3.sayName 和p4.sayName不相等)。

    原型模式:

    定义一个空函数,然后把所有属性和方法都添加到原型上,这样所有的 对象都会共用这些属性和方法。

    1     function Student() {};
    2     Student.prototype.name = "ming";
    3     Student.prototype.age = 20;
    4     Student.prototype.friends = ['qi'];
    5     Student.prototype.sayName = function () {
    6         alert(this.name);
    7     };

    缺点:有些属性不能共享,共享回来带来问题,例如:friends。每位同学的friends 大多都不会相同。

    构造函数与原型的组合:

     1     function Student(name, age, friends) {
     2         this.name = name;
     3         this.age = age;
     4         this.friends = friends;
     5     }
     6     Student.prototype = {
     7         constructor: Student,
     8         sayName: function () {
     9             alert(this.name);
    10         }
    11     };

    总结:构造函数与原型的组合 是一种获得广泛认可的创建自定义类型的方法。 也是上面这些方法中的最优方法。

    /*************************************************************************************************************/

    其实上面的创建对象的方法已经很多了,但是还是有可能出现一些比较特殊的场景,需要继续的优化。

    动态原型模式:

    它是构造函数与原型组合 的一种优化。对于那些共用的属性和方法,如果初始化之后,就不必再重复初始化,提高效率。

     1       function Student(name, age) {
     2           this.name = name;
     3           this.age = age;
     4           if ((typeof this.sayName) != "function") {
     5               Student.prototype.sayName = function () {
     6                   alert(this.name);
     7               }
     8           }
     9       }
    10       var stu = new Person("ming", 20);
    11       //alert(stu instanceof Student);
    12       stu.sayName();

          var stuNew = new Person("hong", 18);
          //alert(stuNew instanceof Student);
          stuNew.sayName();

    当创建多个student对象时,sayName 方法只会初始化一次。

    最后还有一种很有用的创建对象的方式,就是稳妥构造函数。

    稳妥构造函数模式:

    在这个模式中会禁止使用this和new,所有对象没有公共的属性。只能读取变量的值,而不能修改。

          ////稳妥构造函数模式
          function Student(name, age) {
              var o = new Object();
              o.sayName = function () {
                  alert(name);
              }
              return o;
          }
          var stu = Student("ming", 21);
          stu.sayName();
  • 相关阅读:
    如何在CentOS 7中安装最新Git(源码安装)
    centos7安装Lua
    syslog-ng 学习
    syslog-ng内容讲解
    java框架篇---spring IOC 实现原理
    java 过滤器filter使用案例
    jsp-TagLib标签库
    阿里服务器+Centos7.4+Tomcat+JDK部署
    IntelliJ IDEA上创建maven Spring MVC项目
    ServiceStack.Redis之IRedisClient
  • 原文地址:https://www.cnblogs.com/bg57/p/4138382.html
Copyright © 2011-2022 走看看