上一篇随笔讲了封装,这一篇我们说说继承,还是那上一篇猫和狗说事儿

function Dog(name,s){
this.name=name;
this.sex=s;
}
Dog.prototype.type="犬科";
Dog.prototype.spack==function(){
alert("汪汪。。。");
}
function Cat(name,s){
this.name=name;
this.sex=s;
}
Cat.prototype.type="猫科";
Cat.prototype.spack=function(){
alert("喵喵。。。");
}

当然猫和狗都是动物,那他们就有动物的属性,比如需要吃东西,需要呼吸,喝水等等。

现在我们封装一个动物对象:

function Animal(){
this.eat="true";
this.breath="true";
    this.name="动物";
}
Animal.prototype.drink=function(){
  alert("喝水");
};

现在我们需要让猫的对象继承于动物对象的一些属性呢,我们只需要将父对象的属性绑定到子对象上就能让子对象享受父对象的属性和方法,代码如下:

function Dog(name,s){
Animal.apply(this, arguments);
this.name=name;
this.sex=s;
}
function Cat(name,s){
Animal.apply(this, arguments);
this.name=name;
this.sex=s;
}

当然这种方法也是最简单的,还有别的方法:我们可以用prototype来实现,代码如下

function Dog(name,s){
this.name=name;
this.sex=s;
}
Dog.prototype = new Animal();
Dog.prototype.constructor = Dog;
Dog.prototype.type="犬科";
Dog.prototype.spack==function(){
alert("汪汪。。。");
}

这样就让猫和狗都继承了动物的属性和方法了,让我们仔细剖析一下这种方式,在将new Animal()赋给Cat.prototype后,

function Cat(name,s){
this.name=name;
this.sex=s;
}
Cat.prototype = new Animal();
console.log(Cat.prototype);
Cat.prototype.type="猫科";
Cat.prototype.spack=function(){
alert("喵喵。。。");
}

控制台输出

Animal {
breath:"true"
eat:"true"
spack:function ()
type:"猫科"
__proto__:Object
}

打开—proto—,我们看到:

__proto__:Object
drink:function ()
constructor:function Animal()
arguments:null
caller:null
length:
name:"Animal"
prototype:Object
__proto__:function ()
[[FunctionLocation]]:test1.html:
[[Scopes]]:Scopes[]
__proto__:Objec

我们在代码里输出一下:

alert(cat1.constructor == Animal); // true

我们很明显发现constructor指向的是Animal(),在程序中它本应该指向Cat();当我们加入Cat.prototype.constructor = Cat,打开constructor再看时发现

constructor:function Cat(name,s)

有人会说我没家这句话难道不行吗,我没加上述代码程序照样继承了父对象的属性和方法,当然在这种小案例中有可能会行,但是在大项目中这样写代码会在造成继承紊乱,造成不可预知的错误,所以我么需要手动调整Cat.prototype.constructor的值,所以我们在程序中如果给prototype赋值,那么下一步必须是将对象.prototype.constructor的值重新指回到原对构造函数。

当然我们也可以让子构造函数直接继承父构造函数的prototype,代码如下:

function Cat(name,s){
this.name=name;
this.sex=s;
}
Cat.prototype = Animal.prototype;
console.log(Cat.prototype);
Cat.prototype.type="猫科";
Cat.prototype.spack=function(){
alert("喵喵。。。");
}

这种方法好处是高效,不需要重新在新建一个对象,当然缺点也很明显,此刻Animate.prototype和Cat.prototype指向同意数据源,不加Cat.prototype.constructor = Cat时Cat.prototype输出Animal(),加了之后Cat.prototype输出Cat(),貌似对了,可是Animal.prototype此刻居然也输出Cat(),原因是此刻Animate.prototype和Cat.prototype指向同意数据源,当Cat.prototype做出修改时事实上该的是它俩的数据源,所以,这种方法不可取。

当然我们还可以通过中间量的思路解决这个问题,代码如下:

function Bridge(){
}
bridge.prototype=Animal.prototype; Cat.prototype=new Bridge();
Cat.prototype.constructor = Cat;

此刻Bridgr没有添加新的方法和属性,所以它几乎不占内存,而同时我们对prototype进行修改也不会影响其父级对象的prototype

我们将上述代码封装成一个函数,以备使用:

function brideg(p,s){
var F=function(){};
F.prototype=p.prototype;
s.prototype = new F();
s.pprototype.constructor= s;
s.uber= p.prototype;
}

此处uper为子对象添加一个属性,这个属性直接指向父对象的prototype,这等于在子对象上打开一条通道,可以直接调用父对象的方法。

extend(Cat,Animal);
var cat1 = new Cat("咪咪","雄");
alert(cat1.name); // 动物

还有一种继承思路,就是将父对象的所有属性全部拷贝给子属性,那么就相当于子对象继承于父对象了

代码如下

function extend(p,s){
var p1=p.prototype;
var s1=s.prototype;
for(var i in p1){
s1[i]=p1[i];
}
s1.uper=p1;
}

调用如下:

extend2(,Animal, Cat);
var cat1 = new Cat("咪咪","雄");
alert(cat1.name); // 动物

--------------------------------------------------------我是分割线-------------------------------------------------------------

本文参考阮大神文章,地址:

http://www.ruanyifeng.com/blog/2010/05/object-oriented_javascript_inheritance.html

js面向对象(二)——继承的更多相关文章

  1. 捋一捋js面向对象的继承问题

    说到面向对象这个破玩意,曾经一度我都处于很懵逼的状态,那么面向对象究竟是什么呢?其实说白了,所谓面向对象,就是基于类这个概念,来实现封装.继承和多态的一种编程思想罢了.今天我们就来说一下这其中继承的问 ...

  2. js面向对象之继承那点事儿根本就不是事

    继承 说道这个继承,了解object-oriented的朋友都知道,大多oo语言都有两种,一种是接口继承(只继承方法签名):一种是实现继承(继承实际的方法) 奈何js中没有签名,因而只有实现继承,而且 ...

  3. JS面向对象组件 -- 继承的其他方式(类式继承、原型继承)

    继承的其他形式: •类式继承:利用构造函数(类)继承的方式 •原型继承:借助原型来实现对象继承对象   类 : JS是没有类的概念的 , 把JS中的构造函数看做的类 要做属性和方法继承的时候,要分开继 ...

  4. JS——面向对象、继承

    创建对象的方式: 1)单体 <!DOCTYPE html> <html lang="en"> <head> <meta charset=& ...

  5. JS 面向对象之继承 -- 原型链

    ECMAScript只支持实现继承,其实现继承主要是靠原型链来实现. 原型链的基本思想是利用原型让一个引用类型继承另一个引用类型的属性和方法. 简单回顾下构造函数.原型和实例的关系: 每个构造函数都有 ...

  6. js高程(二)-----继承

    首先来讨论一下原型链,上代码 function SuperType(){ this.property = true; } SuperType.prototype.getSuperValue = fun ...

  7. js面向对象之继承-原型继承

    //animal 父类 超类 var Animal = function(name) { this.name = name; this.sayhello = function() { alert(&q ...

  8. JS 面向对象之继承---多种组合继承

    1. 组合继承:又叫伪经典继承,是指将原型链和借用构造函数技术组合在一块的一种继承方式. 下面来看一个例子: function SuperType(name) { this.name = name; ...

  9. Js面向对象构造函数继承

    构造函数继承 <!-- 创建构造函数 --> function Animal(){ this.species= '动物'; } function Dog(name,color){ this ...

  10. JS面向对象笔记二

    菜单导航,<JS面向对象笔记一>,  参考书籍:阮一峰之<JavaScript标准参考教程> 一.构造函数和new命令 二.this关键字 三.构造函数和new命令 四.构造函 ...

随机推荐

  1. (转)TinyHttp源码剖析

    tinyhttpd 是一个不到 500 行的超轻量型 Http Server,用来学习非常不错,可以帮助我们真正理解服务器程序的本质. 看完所有源码,真的感觉有很大收获,无论是 unix 的编程,还是 ...

  2. mybatis-generator命令行生成代码

    目录文件如下: generator.xml文件如下: <?xml version="1.0" encoding="UTF-8"?> <!DOC ...

  3. javascript总结23:javascript 数据类型与变量

    1  基本类型和引用类型 JavaScript中的数据类型分为两类:基本类型和引用类型 基本类型:直接存储值,画图解释 Number.String.Boolean Undefined.Null 引用类 ...

  4. ubuntu创建wifi热点plasma-nm

    第一步:安装 plasma-nm sudo apt-get install plasma-nm 第二步:启动程序 可以使用 Alt+F2 后,搜索 kde-nm-connection-editor 也 ...

  5. 用layer-list做一个卡片背景

    <?xml version="1.0" encoding="utf-8"?> <layer-list xmlns:android=" ...

  6. 异步IO类

    也学习多线程一段时间了,也写了几个简单实用的功能类,也意思到细节的处理的重要性,现在就让我们来写一个稍稍更有用的异步IO的类. 本来想参考Java NIO 中的类,Java NIO作为新io包,本身提 ...

  7. MFC中按钮控件的用法笔记(转)

    VC学习笔记1:按钮的使能与禁止 用ClassWizard的Member Variables为按钮定义变量,如:m_Button1:则m_Button1.EnableWindow(true); 使按钮 ...

  8. Delphi XE8 iOS与Android移动应用开发(APP开发)教程[完整中文版]

    https://item.taobao.com/item.htm?id=536584650957&toSite=main

  9. Android-AndroidStudio Run 'app'安装APK到设备的过程

    1.AndroidStudio 点击Run ‘app’. 2.点击Run ‘app’就会将所有.class文件用SDK工具集处理成.dex, 用SDK工具集将图片/资源/布局文件/AndroidMan ...

  10. ajax使用向Spring MVC发送JSON数据出现 org.springframework.web.HttpMediaTypeNotSupportedException: Content type 'application/x-www-form-urlencoded;charset=UTF-8' not supported错误

    ajax使用向Spring MVC发送JSON数据时,后端Controller在接受JSON数据时报org.springframework.web.HttpMediaTypeNotSupportedE ...