旧文一篇,2014年发布于前端乱炖中,是当时学习的整理,现在拿过来备份凑个篇数;
创建对象
JS中的面向对象是不完整的,没有标准的类的”声明”方式
最常用的类的声明及对象的创建方式如下,不同的书中对其有不同的命名
function Person(name, age) {
// 属性是不相同的,每个有一份
this.name=name;
this.age=age;
}
// 方法是相同的,调用同一个
Person.prototype.showName=function () {
alert(this.name);
};
Person.prototype.showAge=function () {
alert(this.age);
};
var p1=new Person('super', 24);
p1.showName();
p1.showAge();
继承
准则:创建出来的子类实例,
1、用 instanceof 检测父类、子类均返回 true;
2、实例的 constructor 指向该子类;
3、子类添加方法,不会添加到父类上;
同样,JS中实现继承也没有一个标准,所以会有很多实现方式,个人觉得比较常用的两种方式如下:
1、组合继承
function Person(name, age) {
this.name=name;
this.age=age;
}
Person.prototype.showName = function () {
alert(this.name);
};
Person.prototype.showAge = function () {
alert(this.age);
};
function Worker(name, age, job) {
// 1.继承父级的属性
Person.apply(this, arguments);
// 2.添加自己的属性
this.job = job;
}
// 3.继承父级的方法
Worker.prototype = new Person();
Worker.prototype.constructor = Worker;
// 4.添加自己的方法
Worker.prototype.showJob = function () {
alert(this.job);
};
var oW=new Worker('super', 24, 'Programmer');
oW.showName();
oW.showAge();
oW.showJob();
alert(oW instanceof Person); // true
alert(oW instanceof Worker); // true
alert(oW.constructor); // 指向Worker
唯一的缺点就是调用了两次 Persion 方法。
2、寄生组合模式,解决了组合模式的缺点
function object(obj) {
function F(){}
F.prototype = obj;
return new F();
}
function inheritPrototype(subType, superType ) {
var prototype = object(superType.prototype);
prototype.constructor = subType;
subType.prototype = prototype;
}
function Person(name, age) {
this.name=name;
this.age=age;
}
Person.prototype.showName=function () {
alert(this.name);
};
Person.prototype.showAge=function () {
alert(this.age);
};
function Worker(name, age, job) {
// 1.继承父级的属性
Person.apply(this, arguments);
// 2.添加自己的属性
this.job=job;
}
// 3.继承父级的方法
inheritPrototype(Worker, Person);
// 4.添加自己的方法
Worker.prototype.showJob=function () {
alert(this.job);
};
var oW=new Worker('Super', 24, 'Programmer');
oW.showName();
oW.showAge();
oW.showJob();
alert(oW instanceof Person); // true
alert(oW instanceof Worker); // true
alert(oW.constructor); // 指向Worker
个人觉得还是第一种 – 组合继承方便。
3、继承的封装
组合继承模式的封装
// 参数:父类型(构造函数)、子类的构造、子类的方法
function inherit(parentType, childConstructor, methods) {
//Child——子级的构造函数
function Child() {
//arguments -> ['Super', 24, 'Programmer']
// 1.继承父级的属性
parentType.apply(this, arguments);
// 2.添加子级的属性
childConstructor.apply(this, arguments);
}
// 3.继承父级的方法
Child.prototype = new parentType();
Child.prototype.constructor = Child;
// 4.添加子级的方法
for(var i in methods) {
Child.prototype[i] = methods[i];
}
return Child;
}
// ====================== 测试 ====================
function Person(name, age) {
this.name=name;
this.age=age;
}
Person.prototype.showName = function () {
alert(this.name);
};
Person.prototype.showAge = function () {
alert(this.age);
};
//继承
var Worker = inherit( Person, function (name, age, job){
this.job = job;
}, {
showJob: function () {
alert(this.job);
}
});
var oW = new Worker('Super', 24, 'Programmer');
oW.showName();
oW.showAge();
oW.showJob();
alert(oW instanceof Person); // true
alert(oW instanceof Worker); // true
alert(oW.constructor); // 指向 Child
这里只简单的封装了一下所谓的组合继承,实际项目中还真是没有用过继承,有点儿心虚,不好意思往下写了,另一个自己封装吧。
继承在游戏中应该用的多一些吧,现在模块化已经流行开来,似乎比面向对象开发更方便。