您的位置:首页 > Web前端 > JavaScript

JavaScript对象创建与继承总结

2017-10-18 19:13 387 查看
JavaScript中的每个元素都是一个对象,都继承自Object对象,因此可以说Object是JavaScript的根对象。首先说说JavaScript中创建对象的几种常见方式:

1、对象字面量创建对象,如:

var myObject = {
name: '张三',
sex: '男',
age: 25
}
//等价于
var myObject = new Object();
myObject.name = '张三';
myObject.sex = '男';
myObject.age = 25;
//还有常见的定义一个数组
var arr = [];//等价于 var arr = new Array();


2、利用JavaScript内嵌的引用类型创建相关对象,如:

var arr = new Array(5)
var arr = new Array("red", "blue");
/*数组长度为5,注意:JavaScript中数组的长度不是固定的,可以动态改变,数组长度length只是在某个状态下的一个动态值*/

var date = new Date();
var pattern = new RegExp("[bc]at", "i");


3.1、自定义构造函数创建对象(构造函数模式),如:

//构造函数首字母一般大写
function Person(name, age, job){
this.name = name;
this.age = age;
this.job = job;
this.sayName = function(){
console.log(this.name);
};
}
var person = new Person("kitty", 25, "Software Engineer");
//构造函数模式创建对象的缺陷:每个实例对象均有一套自己专属的属性和方法,定义实现同一功能的多个方法显然是一种浪费内存的做法。于是想到把属性和方法定义在构造函数的原型对象中,见方法3.2


在说原型模式之前,先简要介绍一下原型:任何函数在创建的时候,都会包含一个原型属性prototype,指向一个原型对象。初始状态下,原型对象都只包含一个构造函数属性constructor,指向创建此函数的构造函数(一般是Function)。

实例对象与构造函数原型对象的关系:当调用构造函数创建一个实例对象后,该实例内部包含一个指针[[Prototype]],指向构造函数的原型对象,可通过实例的proto属性访问原型对象。

实例对象调用方法:先在实例对象中查找该方法,当实例对象中不存在该方法时,到原型对象中查找,找到,执行。如果存在原型链,会沿着原型链以此查找,例如 toString()方法

alert(Person.prototype.isPrototypeOf(person));//true
alert(Object.getPrototypeOf(person)==Person.prototype);//true


3.2、原型模式

所谓原型模式,就是把对象属性和方法都定义在构造函数的原型对象中,避免每个对象都重复定义属性和方法,如:

//空构造函数
function Person(){
}
//把对象属性和方法都定义在原型对象中
Person.prototype.name = "kitty";
Person.prototype.age = 25;
Person.prototype.job = "Software Engineer";
Person.prototype.sayName = function(){
alert(this.name);
}

var person = new Person();
//原型模式创建对象的缺陷:虽然克服了重复定义多个相同功能函数的缺陷,但也带来新的缺陷,即多个实例对象共享一套属性和方法,只要一个其中实例对象修改属性值,其他的实例对象中的属性值也会被修改。

//综合构造函数模式和原型模式,即对象属性定义在构造函数中,方法定义在构造函数的原型对象中
function Person(name, age, job){
this.name = name;
this.age = age;
this.job = job;
}
Person.prototype.sayName = function(){
alert(this.name);
}
var person1 = new Person("kitty", 25, "Software Engineer");
var person2 = new Person("hello", 25, "Software Engineer");
//此时实例对象person1和person2中的属性互不干扰,公用sayName方法。***这是最常用的创建对象的方法***


最常见、最常用的创建对象的方法就是以上介绍的3种方式了,接下来说说继承。

JavaScript的继承与面向对象语言中的继承不同,JavaScript行数没有签名,故只能继承方法,而不能继承函数名(例Java中的接口继承)。JavaScript实现继承基于原型链。

原理:把某个实例对象复制给另一个对象(构造函数)的原型对象

功能:让一个引用类型继承另一个引用类型的属性和方法

//父构造函数
function FatherObject(){
this.name = "father";
}
FatherObject.prototype.getName = function(){
return this.name;
}
//子构造函数
function SonObject(){
this.name = "son";
}
SonObject.prototype.sayName = function(){
alert(this.name);
}
SonObject.prototype = new FatherObject();
var instance1 = new SonObject();
var instance2 = new SonObject();
alert(instance.sayName());//son
alert(instance.getName());//father

/*原型链:instance._proto_ == SonObject.prototype
而SonObject.prototype被赋值为一个FatherObject对象的实例,SonObject.prototype._proto_== FatherObject.prototype
所以instance对象可以沿着原型链访问以上所有属性和方法。
其实FatherObject.prototype是Object对象的一个实例,原型链最终止于Object对象,这就是为什么JavaScript对象都可以访问toString(),valueOf(),hasOwnProperty()方法的原因*/


原型链继承也有缺陷,上面例子中的instance1和instance2共享FatherObject对象中的name属性,克服这个缺陷,只需要在子构造函数中调用一下父构造函数即可继承属性

function SonObject(){
FatherObject.call(this, name);
this.name = "son";
}


原型式继承:根据一个存在的实例对象创建继承对象实例

function createObject(o){
function F(){};
F.prototype = o;
return new F();
}
//ECAMScript5中规范为Object.create()


寄生式继承:在原型式继承的基础上添加新的属性和方法

function createObject(o){
var clone = Object.create(o)
clone.age = 25;
clone.sayHi = function(){
alert("hi");
}
return clone;
}


尚有不足,后续补全
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  javascript 对象 继承