系统理解javascript面向对象编程
创建对象的四种方式:
(1) 工厂模式:
funciton createPerson(name,age,job){
var o = new Object();
o.name = name;
o.age = age;
o.job = job;
o.sayName = function(){
alert(this.name);
}
return o;
}
var person1 = createPerson("pingzidong",23,"software engineer");
var person2 = createPerson("miaomiao",24,"teacher");
评价:
解决了创建多个相似对象的问题,但是没有解决对象识别的问题
(2) 构造函数模式:
function Person(name,age,job){
this.name = name;
this.age = age;
this.job = job;
this.sayName = function(){
alert(this.name);
};
}
var person1 = new Person("pingzidong",27,"front-end engineer");
var person2 = new Person("pingjunyan",30,"teacher");
评价:
函数的三种用法:
1. 用作构造函数
2. 作为普通函数调用
3. 在另外一个对象的作用域中进行调用
不足:
同一个方法,每当创建一个实例,就需要一个实例一个新的Funtion()对象
(3) 原型模式:
function Person(){}
Person.prototype.name = "pingzidong";
Person.prototype.age = 27;
Person.prototype.job = "soft engineer";
Person.prototype.sayName = function(){
alert(this.name);
}
var person1 = new Person();
var person2 = new Person();
简单写法:
function Person(){}
Person.prototype = {
Constructor:Person,
name:“pingzidong”,
age:27,
job:“soft engineer”,
sayName:function(){
alert(this.name);
}
}
不足:
所有的实例共享属性和方法,对于引用类型的值(对象,数组,function),一个对象更改其值造成另外一个对象的该值的变化
(4) 组合使用构造函数模式和原型模式(普遍使用的模式)
function Person(name,age,job){
this.name = name;
this.age = age;
this.job = job;
this.friends =[“pingzidong”,“mm”];
}
Person.prototype = {
constructor:Person,
sayName:function(){
alert(this.name);
}
}
继承的6种实现方式:
(1) 原型链
function SuperType(){
this.property = true;
this.colors = [“red”,”blue”,”green”];
}
SuperType.prototype.getSuperValue = function(){
return this.property;
}
function SubType(){
this.subproperty = false;
}
SubType.prototype = new SuperType(); // 创建子类型实例时,不能向超类型构造函数传递参数
SubType.prototype.getSubValue = function(){
return this.subproperty;
}
var instance1 = new SubType();
instance1.push(“black”);
alert(instance1.colors)
var instance2 = new SubType();
alert(instance2.colors);
alert(instance.getSuperValue());
评价
(1) 所有的SubType实例共享colors属性,不同实例之间属性值互相影响
(2)创建子类型实例时,不能向超类型传递参数
(2) 借用构造函数
function SuperType(name){
this.name = name;
this.colors = [“red“,”green”];
}
SuperType.prototype.sayHello = function(){
alert(“hello world”);
}
function SubType(){
SuperType.call(this,”pingzidong2“)
}
var instance1 = new SubType();
intance1.colors.push(“black“);
alert(instance1.name);
alert(instance1.colors);
var instance2 = new SubType();
alert(instance2.colors);
评价:
构造函数任务过重,无法复用
在超类型原型定义的方法对子类型不可见
(3) 组合继承
function SuperType(name){
this.name = name;
this.colors = [“red”,”blue”,”black” ];
}
SuperType.prototype.sayName = function(){
alert(this.name);
}
function Subtype(name,age){
SuperType.call(this,name);
this.age = age;
}
SubType.prototype = new SuperType();
SubType.prototype.constructor = SuperType;
SubType.prototype.sayAge = function(){
alert(this.age);
}
var subtype = new SubType(“pppp”,23);
评价:
实现不同实例拥有自己的属性,包括引用属性,同时共享相同的方法
缺点:
2次调用超类型构造函数(父类),一次是在定义子类原型时,一次是在实例化子类时,可以参考寄生组合式继承
(4) 原型式继承
var person = {
name:”fdsfsd”,
friends:[“rd”,”re”,”fds”]
}
function object(o){
function F(){ }
F.prototype = o;
return new F();
}
var another people = object(person);
anotherpeople.name = “FDS”;
anothpeople.friends.push(“dfs”);
var yetanotherpeople = object(person);
yetanotherpeople.friends.push(“fuss”);
alert(person.friends);
评价:
没有构造函数使用原型继承(前提是已有对象)也可以搞定继承
需要注意的是:包含引用类型值的属性始终不用实例会共享,这点和原型链类似
(5) 寄生式继承
function createAnother(original){
var clone = object(original);
clone.sayHi = function(){
alert(“hi“);
}
return clone;
}
(6) 寄生组合式继承
function initPrototype(SubType,SuperType){
var prototype = object(Supertype.prototype);
prototype.constructor = SubType;
SubType.prototype = prototype;
}
function object(o){
function F(){}
F.prototype = o;
return new F();
}
评价:
可替换组合式继承中: SubType.prototype = new SuperType();
替换为: initPrototype(SubType,SuperType)
浙公网安备 33010602011771号