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

javascript 面向对象编程(封装、继承)

2017-07-31 18:39 555 查看
在面向对象编程中,类(class)是对象(object)的模板,定义了同一组对象(又称”实例”)共有的属性和方法。

Javascript语言不支持”类”,但是可以构造函数的方法,模拟出”类”。

构造函数

构造函数就是一个普通的函数,但内部使用了this变量,对构造函数使用 new 运算符就能声称事例,并且this变量会帮定在实例对象上。

function Cat(name,color){
this.name = name;
this.color = color;
}

//每一个构造函数都有一个prototype属性,指向另一个对象。这个对象的所有属性和方法,都会被构造函数的实例继承。
//共有属性和方法可以直接定义在prototype上,指向同一个内存地址
Cat.prototype.type = "猫科动物";
Cat.prototype.eat = function(){
alert("小猫爱吃鱼");
}

var cat1 = new Cat("小白","white");
var cat2 = new Cat("小黑","black");

alert(cat1.eat == cat2.eat); //true


Prototype模式的验证方法

isPrototypeOf() : 用于判断某个prototype对象和某个实例之间的关系

alert(Cat.isPrototypeOf(cat1))   //true
alert(Cat.isPrototypeOf(cat2))   //true


hasOwnPrototype :每个实例化对象都有一个hasOwnPrototype()方法,用于判断某个属性是实例对象属性还是pototype对象属性

alert(cat1.hasOwnPrototype("name"))   //true
alert(cat1.hasOwnPrototype("type"))   //false


in运算符

用于查看某个实例是否为某个对象的属性,不管是实例对象属性还是原型对象的属性

4000
alert("name" in cat1)   //true
alert("type" in cat1)   //true


运算符还可以用来遍历某个对象的所有属性


for(var prop in cat1) { alert("cat1["+prop+"]="+cat1[prop]); }


利用空对象作为中介的构造函数的继承

  function Animal(){ }
    Animal.prototype.species = "动物";
    
function Cat(name,color){
    this.name = name;
    this.color = color;
  }
  //使猫继承于动物  封装成inherits()
function inherits(Child, Parent) {
var F = function () {};
F.prototype = Parent.prototype;
Child.prototype = new F();
Child.prototype.constructor = Child;
}

//使用该方法
inherits(Cat,Animal);
var cat1 = new Cat("大白","whiteMax");
alert(cat1.species)  //动物


class继承

从ES6开始关键字class被引入javascript中,目的:让定义类更简单

比较:JavaScript的对象模型是基于原型实现的,特点是简单,缺点是理解起来比传统的类-实例模型要困难,最大的缺点是继承的实现需要编写大量代码,并且需要正确实现原型链。

class类定义

class Cat{
constructor(name,color){
this.name = name;
this.color = color;
};
eat(){
alert("小猫爱吃鱼")
}
}
//实例化
var cat1 = new Cat("小白","white");
var cat2 = new Cat("小黑","black");

console.log(cat1.eat === cat2.eat)   //true
console.log(cat1.name === cat2.name)  //false
console.log(Cat.isPrototypeOf(cat1))  //false  //不是通过原型对象创建的


class继承

class Animal{
constructor(name){
this.name = name;
this.species = "动物"
}
}

class Cat extends Animal{
constructor(name,color){
super(name);   //继承父类的constructor(name)
this.color = color;
}

hello(){
return "Hello, "+this.name +"!";
}
}

var cat1  = new Cat("小白","white");
var cat2 = new Cat("小黑","black");

console.log(new Cat('x') instanceof Animal)    //true
console.log(cat1.species)  //动物   -->  证明Cat继承Animal类
console.log(cat1.hello() === cat2.hello());  //false


extends则表示原型链对象来自Animal。子类的构造函数可能会与父类不太相同,例如,Cat需要name和color两个参数,并且需要通过super(name)来调用父类的构造函数,否则父类的name属性无法正常初始化。

Cat已经自动获得了父类Animal的species属性,我们又在子类中定义了新的hello()方法。

ES6引入的class和原有的JavaScript原型继承实际上它们没有任何区别,class的作用就是让JavaScript引擎去实现原来需要我们自己编写的原型链代码。简而言之,用class的好处就是极大地简化了原型链代码。

需要一个工具把class代码转换为传统的prototype代码,可以试试Babel这个工具。

参考链接

Javascript 面向对象编程(一):封装

Javascript面向对象编程(二):构造函数的继承

Javascript面向对象编程(三):非构造函数的继承

原型继承

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