JS设计模式——4.继承(概念)
类式继承
0.构造函数
一个简单的Person类
function Person(name){
this.name = name;
}
Person.prototype.getName = function(){
return this.name;
}
1.原型链实现继承
未封装extend函数继承
继承步骤如下:
step 1:创建继承类的构造函数
step 2:设置继承类的原型链为父类构造函数。
step 3:调整继承类的构造函数。
step 4:创建继承类
function Author(name, books){
Person.call(this, name); //step 1
this.books = books;
}
Author.prototype = new Person(); //step 2
Author.prototype.constructor = Author; // step 3
Author.prototype.getBooks = function(){
return this.books;
};
var author = new Author('ysy',['js desgin']); // step 4
简单封装extend函数继承
function extend(subClass, superClass){
var F = function(){};
F.prototype = superClass.prototype;
subClass.prototype = new F(); // step 2
subClass.prototype.constructor = subClass; // step3
}
这种展示了封装的原理,但是step1并没有封装进来,而最重要的是step1中会产生对Person的耦合。
高级封装extend函数继承
function extend(subClass, superClass){
var F = function(){};
F.prototype = superClass.prototype;
subClass.prototype = new F();
subClass.prototype.constructor = subClass;
subClass.superclass = superClass.prototype;
if(superClass.prototype.constructor == Object.prototype.constructor){
superClass.prototype.constructor = superClass;
}
}
这样在构建子类的构造函数时示例如下:
function Author(name, books){
Author.superclass.constructor.call(this, name);
this.books = books;
}
extend(Author, Person);
原型式继承
0.原型对象
直接定义一个对象即可
var Person = {
name: 'ysy',
getName: function(){
return this.name;
}
}
1.对继承而来的成员的读和写的不对等性
这个其实很好理解,如果在读属性之前还未对继承而来的属性进行赋值操作,那么读的就是super中的属性,而此时写的话,却是对sub中的写。
当然,一旦写过之后,读和写就是对等的了。
这个简单问题就不再给出代码了。如果你不懂,就去彻底了解一下原型链。
2.clone函数
function clone(obj){
function F(){}
F.prototype = obj;
return new F;
}
3.继承的实现
var Author = clone(Person);
Author.books = [];
Author.getBooks = function(){
return this.books;
}
貌似这个继承的实现要简单好多哇。
继承与封装
只有公用和特权成员会被继承下来。
因此,门户大开型式最适合派生自雷的。它们的所有成员都是公开的,因此可以被遗传给子类。如果某个成员需要稍加隐藏,可以用下划线规范。
在派生具有真正的私有成员的类时,特权方法是公用的,可以被继承,因此也就可以访问父类的私有成员,但是我们不能在子类中添加能够直接访问他们的新的特权方法。
掺元类
有一种重用代码的方法不需要用到严格的继承。
他的做法是:先创建一个包含各种通用方法的类,然后再用他扩充其他类。
这种包含通用方法的类就是掺元类。
下面定义一个简单的掺元类:
var Mix = function(){};
Mix.prototype = {
serialize: function(){
var output = [];
for(key in this){
output.push(key+':'+this[key]);
}
return output.join(',');
}
}
augment(Author, Mix);
var author = new Author('Ross', ['js desgin']);
augment其实很简单。他用一个for in将giving class的prototype中的每个成员都添加到receiving class中。
function augment(rclass, gclass){
if(arguments[2]){ //giving more than 3 paras
for(var i=2, len=arguments.length; i<len; i++){
rclass.prototype[arguments[i]] = gclass.prototype[arguments[i]];
}
}else{
for(methodName in gclass.prototype){
if(!rclass.prototype[methodName]){
rclass.prototype[methodName] = gclass.prototype[methodName];
}
}
}
}
上面的方法还可以指明只继承其中的部分成员。
掺元类的重大有点就是可以实现多继承效果,其他的方法就没法了,因为一个对象只能有一个原型对象。
JS设计模式——4.继承(概念)的更多相关文章
- JS设计模式——4.继承(示例)
目的 我们的目的就是编写一个用于创建和管理就地编辑域的可重用的模块化API.它是指网页上的一段普通文本被点击后就变成一个配有一些按钮的表单域,以便用户就地对这段文本进行编辑. 思路 当用户点击时 1. ...
- JS设计模式——7.工厂模式(概念)
工厂模式 本章讨论两种工厂模式: 简单工厂模式 使用一个类(通常是一个单体)来生成实例. 使用场景:假设你想开几个自行车商店(创建自行车实例,组装它,清洗它,出售它),每个店都有几种型号的自行车出售. ...
- js设计模式--------基本概念的理解
1.闭包,前面已经说过,这里不再做说明 2.封装 对于JS而言,他不像java一样存在私有,公有 ,可以让对象在一些细节方面存在差异,降低他们的耦合程度,对数据做一些约束,我们可以更容易调试,封 ...
- JS设计模式(一)
刚入职时,看过一段时间的设计模式,似懂非懂.不知不觉过去七个月了,对JS的理解更深刻了,数据结构与算法的基础也基本上算是过了一遍了,接下来要把设计模式搞定,然后不再深层次研究JS了,而是学习前端自动化 ...
- JS创建对象、继承原型、ES6中class继承
面向对象编程:java中对象的两个基本概念:1.类:类是对象的模板,比如说Leader 这个是泛称领导,并不特指谁.2:实例:实例是根据类创建的对象,根据类Leader可以创建出很多实例:liyi,y ...
- JS设计模式一:单例模式
单例模式 单例模式也称作为单子模式,更多的也叫做单体模式.为软件设计中较为简单但是最为常用的一种设计模式. 下面是维基百科对单例模式的介绍: 在应用单例模式时,生成单例 ...
- JAVA之旅(六)——单例设计模式,继承extends,聚集关系,子父类变量关系,super,覆盖
JAVA之旅(六)--单例设计模式,继承extends,聚集关系,子父类变量关系,super,覆盖 java也越来越深入了,大家加油吧!咱们一步步来 一.单例设计模式 什么是设计模式? JAVA当中有 ...
- 前端笔记之JavaScript面向对象(三)初识ES6&underscore.js&EChart.js&设计模式&贪吃蛇开发
一.ES6语法 ES6中对数组新增了几个函数:map().filter().reduce() ES5新增的forEach(). 都是一些语法糖. 1.1 forEach()遍历数组 forEach() ...
- 【学习笔记】六:面向对象的程序设计——理解JS中的对象属性、创建对象、JS中的继承
ES中没有类的概念,这也使其对象和其他语言中的对象有所不同,ES中定义对象为:“无序属性的集合,其属性包含基本值.对象或者函数”.现在常用的创建单个对象的方法为对象字面量形式.在常见多个对象时,使用工 ...
随机推荐
- ajax跨域问题(三种解决方案)
为什么会出现跨域 跨域问题来源于JavaScript的同源策略,即只有 协议+主机名+端口号 (如存在)相同,则允许相互访问.也就是说JavaScript只能访问和操作自己域下的资源,不能访问和操作其 ...
- mysql中联合查询
联合查询union 一个翻译问题的解释: 在mysql的手册中,将连接查询(Join)翻译为联合查询: 而联合查询(union),没有明确翻译. 但: 在通常的书籍或文章中,join被翻译为“连接”查 ...
- 第200天:js---常用string原型扩展
一.常用string原型扩展 1.在字符串末尾追加字符串 /** 在字符串末尾追加字符串 **/ String.prototype.append = function (str) { return t ...
- HDU4473_Exam
很考验智商的一个题目,赛后看完别人的题解后秒懂了. 首先定义一个函数f(x)表示a,b的有序组合情况数使得a*b为x的一个约数. 现在给定你一个n,要你求出f(1)+f(2)+……+f(n): 题目智 ...
- luogu 1066 引水入城(bfs+贪心)
90分,有一个点TLE.... 首先可以证明一个东西,如果从上面一排的某个点bfs一次到最下面一排的饮水点不是一个区间的话,那么最后一定所有饮水点不会被覆盖完的. 证明考虑反证法. 所以从上面一排的每 ...
- 线段树之Sum
题面: 给定一数列,规定有两种操作,一是修改某个元素,二是求区间的连续和. Input: 输入数据第一行包含两个正整数n,m(n<=100000,m<=500000),以下是m行, 每行有 ...
- 【MediaElement】WPF视频播放器【1】
一.前言 前两天上峰要求做一个软件使用向导,使用WPF制作.这不,这两天从一张白纸开始学起,做一个播放演示视频的使用向导.以下是粗设计的原型代码: 二.效果图 三.代码 前台代码: < ...
- 使用Unity5.1进行VR开发的配置(最新的未必是最好的!!!)
随着Unity5.1的发布,之前的Oculus Rift和Gear VR 开发流程发生了巨大的变化,这也算是小白鼠们必须付出的代价了~ 那么Unity5.1和Oculus的整合究竟发生了哪些变化,对开 ...
- NOIP模拟
1.要选一个{1,2,...n}的子集使得假如a和b在所选集合里且(a+b)/2∈{1,2,...n}那么(a+b)/2也在所选集合里 f[i]=2*f[i-1]-f[i-2]+g[i] g[n]:选 ...
- 【learning】快速沃尔什变换FWT
问题描述 已知\(A(x)\)和\(B(x)\),\(C[i]=\sum\limits_{j\otimes k=i}A[j]*B[k]\),求\(C\) 其中\(\otimes\)是三种位运算的其中一 ...