理解js对象继承的N种模式


Posted in Javascript onJanuary 25, 2016

本文分享了js对象继承的N种模式,供大家参考。

一、原型链继承

function Person(){};

Person.prototype = {
  constructor: Person,
  name: "Oliver"
};
    
function People(){};

People.prototype = new Person();
People.prototype.constructor = People;
People.prototype.sayName = function(){
  return this.name;
};

var ins = new People();

console.log(ins.sayName());

二、借用构造函数(伪造对象,经典继承)

1、无参数

function SuperType(){
  this.color = ["red","yellow","white"];
}
function SubType(){
  SuperType.call(this);
}

var instance1 = new SubType();
var instance2 = new SubType();

instance1.color.pop();
console.log(instance1.color); //["red", "yellow"]
console.log(instance2.color); //["red", "yellow", "white"]

2、有参数

function SuperType(name){
  this.name = name;
  this.number = [21,32,14,1];
}
function SubType(name,age){
  SuperType.call(this,name);
  this.age = age;
}

var instance1 = new SubType("Oliver",18);
var instance2 = new SubType("Troy",24);

instance2.number.pop();

console.log(instance1.name + instance1.age + instance1.number); //Oliver1821,32,14,1
console.log(instance2.name + instance2.age + instance2.number); //Troy2421,32,14

三、组合继承(伪经典继承)

1、无参数

function SuperType(){
  this.color = ["red","yellow","white"];
}
SuperType.prototype.sayColor = function(){
  return this.color;
};

function SubType(){
  SuperType.call(this);
  this.number = 321;
}
SubType.prototype = new SuperType();
SubType.prototype.constructor = SubType;
SubType.prototype.sayNumber = function(){
  return this.number;
};

var instance1 = new SubType();
var instance2 = new SubType();

instance2.color.pop();
console.log(instance1.color + instance1.number); //red,yellow,white321
console.log(instance2.color + instance2.number); //red,yellow321

2、有参数

function SuperType(name){
  this.name = name;
  this.number = [32,1342,11,1];
}
SuperType.prototype.sayName = function(){
  return this.name;
};

function SubType(name,age){
  SuperType.call(this,name);
  this.age = age;
}
SubType.prototype = new SuperType();
SubType.prototype.constructor = SubType;
SubType.prototype.sayAge = function(){
  return this.age;
};

var instance1 = new SubType("Oliver",18);
var instance2 = new SubType("Troy",24);

instance2.number.pop();
console.log(instance1.sayName() + instance1.sayAge() + instance1.number); //Oliver1832,1342,11,1
console.log(instance2.sayName() + instance2.sayAge() + instance2.number); //Troy2432,1342,11

三、寄生组合式继承(引用类型最理想的范式)

function inheritPrototype(subType,superType){
  var prototype = Object(superType.prototype);
  prototype.constructor = subType;
  subType.prototype = prototype;
}

function SuperType(name){
  this.name = name;
  this.number = [321,321,43];
}
SuperType.prototype.sayName = function(){
  return this.name;
};

function SubType(name,age){
  SuperType.call(this,name);
  this.age = age;
}
inheritPrototype(SubType,SuperType);
SubType.prototype.sayAge = function(){
  return this.age;
};

var instance1 = new SubType("Oliver",18);
var instance2 = new SubType("Troy",24);
instance2.number.pop();

console.log(instance1.sayName() + instance1.sayAge() + instance1.number); //Oliver18321,321,43
console.log(instance2.sayName() + instance2.sayAge() + instance2.number); //Troy24321,321

或者可以把inheritPrototype 函数写成下面这样:

function inheritPrototype(SubType,SuperType){
  SubType.prototype = new SuperType();
  SubType.prototype.constructor = SubType;
}

四、原型式继承(用于共享引用类型的值,与寄生式类似)

1、传统版(先定义object() 函数,再继承)

function object(o){
  function F(){};
  F.prototype = o;
  return new F();
}

var SuperType = {
  name: "Oliver",
  number: [321,321,4532,1]
};

var SubType1 = object(SuperType);
var SubType2 = object(SuperType);

SubType1.name = "Troy";
SubType1.number.pop();

SubType2.name = "Alice";
SubType2.number.pop();

console.log(SubType1.name + SubType2.name + SubType1.number + SubType2.number + SuperType.name + SuperType.number); //TroyAlice321,321321,321Oliver321,321

ECMAScript 5 版(直接用Object.create(),再继承)

var SuperType = {
  name: "Oliver",
  number: [321,321,4532,1]
};

var SubType1 = Object.create(SuperType); //省略了定义object()函数
var SubType2 = Object.create(SuperType);

SubType1.name = "Troy";
SubType1.number.pop();

SubType2.name = "Alice";
SubType2.number.pop();

console.log(SubType1.name + SubType2.name + SubType1.number + SubType2.number + SuperType.name + SuperType.number); //TroyAlice321,321321,321Oliver321,321

ECMAScript 5 简写版(定义Object.create()的第二个参数,再继承)

var SuperType = {
  name: "Oliver",
  number: [321,321,4532,1]
};

var SubType1 = Object.create(SuperType,{
  name: {
    value : "Troy"
  }
});
var SubType2 = Object.create(SuperType,{
  name: {
    value : "Alice"
  }
});

SubType1.number.pop();
SubType2.number.pop();

console.log(SubType1.name + SubType2.name + SubType1.number + SubType2.number + SuperType.name + SuperType.number); //TroyAlice321,321321,321Oliver321,321

寄生式继承(用于共享引用类型的值,与原型式类似)

function createAnother(original){
  var clone = Object(original);
  clone.sayHi = function(){
    return "Hi";
  };
  return clone;
}

var person = {
  name: "Oliver",
  number: [13,21,31,1]
};

var anotherPerson = createAnother(person);
anotherPerson.number.pop();

console.log(anotherPerson.sayHi() + anotherPerson.number); //Hi13,21,31
console.log(person.number); //13,21,31

以上就是本文的全部内容,希望对大家的学习有所帮助。

Javascript 相关文章推荐
用javascript动态调整iframe高度的代码
Apr 10 Javascript
解决jquery的datepicker的本地化以及Today问题
May 23 Javascript
一个JavaScript处理textarea中的字符成每一行实例
Sep 22 Javascript
JS提示:Uncaught SyntaxError: Unexpected token ILLEGAL错误的解决方法
Aug 19 Javascript
JS异步加载的三种实现方式
Mar 16 Javascript
node.js用fs.rename强制重命名或移动文件夹的方法
Dec 27 Javascript
小程序实现自定义导航栏适配完美版
Apr 02 Javascript
vue回到顶部监听滚动事件详解
Aug 02 Javascript
NProgress显示顶部进度条效果及使用详解
Sep 21 Javascript
原生javascript如何实现共享onload事件
Jul 03 Javascript
vue实现一个获取按键展示快捷键效果的Input组件
Jan 13 Vue.js
小程序wx.getUserProfile接口的具体使用
Jun 02 Javascript
解决js函数闭包内存泄露问题的办法
Jan 25 #Javascript
JavaScript数据类型学习笔记
Jan 25 #Javascript
分步解析JavaScript实现tab选项卡自动切换功能
Jan 25 #Javascript
jQuery form 表单验证插件(fieldValue)校验表单
Jan 24 #Javascript
Jquery实现纵向横向菜单
Jan 24 #Javascript
JavaScript、jQuery与Ajax的关系
Jan 24 #Javascript
JavaScript jquery及AJAX小结
Jan 24 #Javascript
You might like
PHP输出图像imagegif、imagejpeg与imagepng函数用法分析
2016/11/14 PHP
php中get_magic_quotes_gpc()函数说明
2017/02/06 PHP
PHP实现压缩图片尺寸并转为jpg格式的方法示例
2018/05/10 PHP
js 无提示关闭浏览器页面的代码
2010/03/09 Javascript
JavaScript 原型学习总结
2010/10/29 Javascript
javascript获取鼠标位置部分的实例代码(兼容IE,FF)
2013/08/05 Javascript
jQuery实现密保互斥问题解决方案
2013/08/16 Javascript
jQuery手机浏览器中拖拽动作的艰难性分析
2015/02/04 Javascript
javascript文本框内输入文字倒计数的方法
2015/02/24 Javascript
jquery实现图片左右切换的方法
2015/05/07 Javascript
JavaScript 过滤关键字
2017/03/20 Javascript
基于vue开发的在线付费课程应用过程
2018/01/25 Javascript
妙用缓存调用链实现JS方法的重载
2018/04/30 Javascript
一步快速解决微信小程序中textarea层级太高遮挡其他组件
2019/03/04 Javascript
[01:00:06]加油DOTA_EP01_网络版
2014/08/09 DOTA
[48:21]Mski vs VGJ.S Supermajor小组赛C组 BO3 第一场 6.3
2018/06/04 DOTA
详解Python中使用base64模块来处理base64编码的方法
2016/07/01 Python
Python实现一个Git日志统计分析的小工具
2017/12/14 Python
python字符串的方法与操作大全
2018/01/30 Python
python 实现在Excel末尾增加新行
2018/05/02 Python
Python 计算任意两向量之间的夹角方法
2019/07/05 Python
python ImageDraw类实现几何图形的绘制与文字的绘制
2020/02/26 Python
python如何实时获取tcpdump输出
2020/09/16 Python
Big Green Smile法国:领先的英国有机和天然产品在线商店
2021/01/02 全球购物
如何让Java程序执行效率更高
2014/06/25 面试题
Java面试题:请说出如下代码的输出结果
2013/04/22 面试题
给同学的道歉信
2014/01/16 职场文书
党的群众教育实践活动实施方案
2014/06/12 职场文书
2014大学生党员评议个人总结
2014/09/22 职场文书
见习期个人总结
2015/03/05 职场文书
确保工程质量承诺书
2015/04/29 职场文书
员工拾金不昧表扬稿
2015/05/05 职场文书
2015年计划生育责任书
2015/05/08 职场文书
使用python向MongoDB插入时间字段的操作
2021/05/18 Python
python用tkinter开发的扫雷游戏
2021/06/01 Python
Java 深入探究讲解简单工厂模式
2022/04/07 Java/Android