上篇介绍了关于 JavaScript 面向编程的概念和需要掌握的一些简单的知识点,那么本章具体介绍一下 JavaScript 有哪些面向对象的编程和使用这些编程的好处与坏处。

1、JavaScript 创建对象的基本模式。

<script>
   var people = new  Object();
   people.name = '孙悟空';
   people.weapon = '金箍棒';

   // this 是指的当前作用域下的对象,注意和谁调用这个方法有关,和在哪定义没关系
   // 这里也可以简单理解为 this 就指的这个函数属于谁,属于谁 this 就是指的谁,这里就是对象 People
   people.run = function(){
    return this.name + '的武器是' + this.weapon;
   };
   alert(this.weapon);        // 弹出 undefined ,这时的 this 是指的全局对象,而对象下没有weapon属性,所以找不到
   alert(people.name);        // 弹出 孙悟空,调用对象里面的属性
   alert(people.run());       // 弹出 孙悟空的武器是金箍棒,调用对象里面的函数
</script>

这种方法就是简单基本的创建对象,但是呢,这种方法是由缺陷的:
如果是创建一个两个对象还是可以使用这个方法,但是如果多个就会显得很繁琐,创建一个要写很多相同的代码,而且占内存效率低,不利于后期的维护处理。在创建很多个的时候也不能看出第一个原型和其他的有任何的联系,所以为了解决这上面的几个缺陷,我们使用第二种方法,创建对象的工厂模式。

① 使用简单的创建对象就会比较繁琐,需要重复很多相同的步骤。
② 实例与原型之间,没有任何办法可以看出有什么联系。
2、JavaScript 创建对象的工厂模式。

所谓的工厂模式就是指,使用创建并返回特定类型的对象的“工厂函数”(叫法不同,不要纠结,其实也就是把创建的对象封装到函数里面调用而已)。

<script>
   function creatPeople(name,weapon){
    var people = new Object();      // 可以类比为加工对象的原材料
    people.name = name;
    people.weapon = weapon;
    people.run = function(){
    return this.name + '的武器是' + this.weapon;
   };
    return people;              // 注意一定要将创建的对象返回
   }
   var wukong = creatPeople('孙悟空','金箍棒');
   var bajie = creatPeople('八戒','钉耙');
   alert(wukong.run());             // 弹出 孙悟空的武器是金箍棒
   alert(wukong.run);               // 弹出 run() 函数本身
   alert(bajie.run);                // 弹出 run() 函数本身
   alert(wukong.run == bajie.run);      // 弹出的是 false ,不相等(判断两个函数是否相等)
   // 因为函数一个‘引用类型’,当我们赋值函数的时候,赋值的是引用的地址,
   // 虽然弹出的两个函数一样的,但是引用的地址是不相同的,所以会占用两个地址空间的内存 ---浪费内存
</script>

在我们创建的函数里面添加两个参数(name,weapon),把需要传递的参数给对象 People 的属性,作为属性值,然后实例化创建的函数(带有参数),最后调用。这种方法是可以解决上面基本模式所带来的限制个数的缺陷,通过实例化可以需要多少个就创建多少个,只要附带的参数改变就可以。虽然解决了上面基本模式的限制缺陷,但也还是有自己的缺陷:

① 仍然不能反映出他们使用得一个原型对象的实例(都是用creatPeolpe()创建的)
② 在实例化创建对象的时候没有使用 new 关键字(var p = new Object())
③ 会造成资源浪费,因为每生成一个实例,都会增加一个重复的内容,多占一些内存
为了解决工厂模式所出现的这一系列问题呢,我们也有方法,那就是要用到第三种方法,创建对象的构造函数模式。