一、工厂模式
工厂模式是我们最常用的实例化对象模式了,是用工厂方法代替new操作的一种模式。工厂模式就相当于创建实例对象的new,所以以后new时就要多个心眼,是否可以考虑使用工厂模式,虽然这样做,可能多做一些工作,但会给你系统带来更大的可扩展性和尽量少的修改量。
工厂模式简单来说就是:调用函数 返回对象 在函数里实例化对象 直接返回对象
<script>
function stu(){
var s=new Object();//实例化对象
s.name="张三";
return s;
}
stu();
</script>
工厂模式主要的优点是消除对象间的耦合,通过使用工程方法而不是new关键字。将所有实例化的代码集中在一个位置防止代码重复。解决了重复实例化的问题。但是,工厂模式没有解决对象识别问题,即创建的所有实例都是Object类型。
为了解决这个问题,就有了构造函数模式。
二、构造函数模式
构造函数模式中可以应用原型链
<script>
function stutent(name,sex){
this.name=name;
this.sex=sex;
this.eat=function(){
}
}
var s1=new stutent("小花","女");
var s2=new stutent("小明","男");
console.log(s1 instanceof Object);//true
console.log(s1 instanceof stutent);//true
</script>
构造的函数stutent()有一个prototype属性,这个属性是一个指针,指向一个对象stutent.prototype (原型对象);
实例s1 s2有_proto_属性,指向stutent.prototype ;
构造函数和实例共享stutent.prototype 里的属性和方法 ;stutent.prototype 里有一个constructor属性,constructor属性是一个指针,指向stutent函数,所以,实例指向了stutent函数,那么实例共享了构造函数的属性和方法,构造函数、实例、原型对象里所有的属性和方法 都是共享的。
构造函数解决了对象识别问题,我们创建的对所有对象既是Object的实例,同时,也是构造函数的实例。根据代码输出的判断结果可以得到验证。
构造函数和普通函数的区别
构造函数:
<script>
function stutent() {
console.log(this);//this指向stutent
}
var stu=new stutent();
</script>
普通函数:
<script>
function stutent(){
console.log(this);//this指向window
}
stutent();
</script>
根据上面两段代码,可以看出两种函数的区别在于函数的使用方式。
另外,两种函数中涉及的this指向不同,看一下输出结果:
构造函数解决了工厂模式的缺点,但是它自身的缺点是每个new出来的实例 里的方法都要重新创建一遍。那么,怎么解决这个问题呢?
看一下另一种模式——原型模式
三、原型模式
我们创建的每个函数都有一个prototype(原型)属性,这个属性是一个指针,指向一个对象,而这个对象的用途是包含可以由特定类型的所有实例共享的属性和方法。
使用原型对象的好处是可以让所有对象实例共享它所包含的属性和方法。也就是说,不必在构造函数中定义对象实例的信息,而是将这些信息添加到原型对象中。
<script>
function cat(){
}
cat.prototype.name="小猫";
cat.prototype.eat=function(){
console.log("小猫吃鱼")
};
var m=new cat();
m.eat();
var n=new cat();
n.eat();
console.log(n.eat);
console.log(m.eat== n.eat);//true
</script>
输出结果:
与构造函数相比,原型模式把公共方法提出来放到prototype对象里。每个实例 的_proto_指针 指向这个对象,所以所有实例的公共方法 是同一个,避免了内存浪费。
四、单例模式
单例模式涉及到一个单一的类,该类负责创建自己的对象,同时确保只有单个对象被创建。这个类提供了一种访问其唯一的对象的方式,可以直接访问,不需要实例化该类的对象。
注意:
- 单例类只能有一个实例。
- 单例类必须自己创建自己的唯一实例。
- 单例类必须给所有其他对象提供这一实例。
<script>
var data=(function(){
function stutents(){
this.name="小花";
}
function getstu(){
var s=new stutents();
return s;
}
return{
info:getstu()
}
})();
console.log(data);
</script>
输出结果: