function Person(name){
this.name=name;
this.sayName=function(){
alert(this.name);
}
}
var p1=new Person('张三');
var p2=new Person('李四');
alert(p1.sayName==p2.sayName);//false
//第一步改进,将公共的方法提取出来(当我们每次创建对象的时候就要独立的开辟一块Person空间,每个sayName方法都不一样)
function Person(name){
this.name=name;
this.sayName=sayName;
}
function sayName(){
alert(this.name);
}
var p1=new Person('张三');
var p2=new Person('李四');
alert(p1.sayName==p2.sayName);//true
//但是由于sayName是person这个类特有的方法,所以这样写仍不合理
//第二次改进,利用javascript的原型,将公共的方法提取出来放到原型对象上
(每一个javascript对象都对应着一个原型对象,由原型对象创建声明的方法,是被该类所有实例对象所共享的)
注:原型对象是Object类型,但是其构造器指向具体的类模板,即 Person.prototype的类型是Object,但是构造器是Person模板
function Person(name){
this.name=name;
}
Person.prototype.sayName=function(){
alert(this.name);
}
var p1=new Person('张三');
p1.sayName();//张三
var p2=new Person('李四');
p2.sayName();//李四
alert(p1.sayName==p2.sayName);//true
//利用原型对象实现继承
//定义父类
var Person =function(name){
this.name=name;
}
//alert(Person.prototype.constructor);//原型对象的构造器,默认是当前类的模板
Person.prototype={ //当Person.prototype={}时就将Person的原型对象的构造器设为Object,所以要还原构造器
constructor:Person,//还原构造器
id:100
};
//定义子类
var Boy=function(sex,age){
this.age=age;
this.sex=sex;
}
//实现原型继承,子类继承了父类的模板和原型对象(子类的原型对象指向父类的实例对象)
Boy.prototype=new Person('李四');
var b=new Boy('男',12);
alert(b.name+b.sex+b.age+b.id);//李四男12100,说明继承了父类的模板和原型对象
//以上写法虽然实现了继承,但是并不是我们一般的预想结构var b=new Boy('李四','男',12);这种形式
//改进继承,利用函数绑定(call)
//定义父类
var Person =function(name){
this.name=name;
}
Person.prototype={
constructor:Person,
id:100
};
var Boy=function(name,sex,age){
Person.call(this,name);//Person类也是一个function所以可以利用函数绑定,构造函数继承,绑定了一次模板
this.age=age;
this.sex=sex;
}
//实现原型继承,子类继承了父类的模板和原型对象(子类的原型对象指向父类的实例对象)
Boy.prototype=new Person();
var b=new Boy('李四','男',12);
alert(b.name+b.sex+b.age+b.id);//李四男12100,说明继承了父类的模板和原型对象
//该方法虽然满足了形式,但是继承了两次模板一次原型对象,当父类较大时,是一种消耗
//最终版 继承了一次模板一次原型对象
function myextend(sub,sup){
var F = function() {},//定义一个空函数作为中转函数
subclassProto,//子类的原型对象
superclassProto = sup.prototype;//吧父类的原型对象交给superclassProto
F.prototype = superclassProto;//中转,空函数的原型对象就是父类的原型对象
subclassProto = sub.prototype = new F();//原型继承,继承父类的空模板和原型
subclassProto.constructor = sub;//还原构造函数
sub.sup = superclassProto;
//为了保险
if (superclassProto.constructor === Object.prototype.constructor) {
superclassProto.constructor = sup;
}
}
//定义父类
var Person =function(name){
this.name=name;
}
Person.prototype={ //当Person.prototype={}时就将Person的原型对象的构造器设为Object,所以要还原构造器
constructor:Person,//还原构造器
id:100
};
//定义子类
var Boy=function(name,sex,age){
Person.call(this,name);
this.age=age;
this.sex=sex;
}
myextend(Boy,Person);
var b=new Boy('李四','男',12);
alert(b.name+b.sex+b.age+b.id);//李四男12100