Javascript 继承和多态
近期通过一些巧合 或者说 思想转变吧 。。。
想通过blog && 公众号 (个人公众号: KeepinJS)去记录自己的Javascript深度学习的内容,从而达到 进一步的自我提升。
js面向对象设计 很多都会用到 原型继承和多态 再加以封装 我通过一些大佬视频 和 学习博客 来分享一波自己的见解 如果有描述不当之处 还请及时指正 => QQ :2070994423 ;Email:2070994423@qq.com 或者在我的公众号上留言,我看到的话,有时间会给予回复和沟通,谢谢!
基础知识不多赘述,来看以下几种继承方式:
原型继承
这里可以通过构造函数创建父类实例,父类实例可以根据不同的参数定义不同的实例属性name,当我们使用原型继承的时候,将子类构造函数原型指向父类实例的时候,再创建子类实例的时候,并不能定义子类的属性,也就是说,虽然父类原型上的方法可以通过这种方式继承下来,但是父类的构造方法(即定义实例属性name)并没有继承下来。
并且,如果没有在创建父类实例的时候定义父类实例的名字,那么,子类是不知道自己继承的父类实例的名字是什么。
所以这种继承是最简单,它只是实现了父类定义的属性和方法。
子类构造函数内调用父类构造函数
通过在子类构造函数内调用父类构造函数,实现this指向的改变,可以实现创建子类实例的时候,它们都会有自己私有的属性值
,每个子类实例都是独一无二的。但是这里是不是看出问题了,子类又不能调用父类原型上的方法,只是继承了父类构造函数定义实例属性的方法,因此,这也是不合适的。
组合继承
这样,不仅可以继承父类构造函数初始化实例属性的方法,也可以调用父类原型上的方法,一举两得。
但是,这里会存在一个问题,new Person()的时候调用一次父类构造函数,子类创建实例的时候又调用了一次父类的构造函数,是不是调用了两次,并且这样的继承必须要创建一个父类实例,有没有办法去减少这样多次调用构造函数和强制调用呢??
寄生组合式继承
这里解析一波Object.create方法,官方定义如下:
Object.create(obj)
方法创建一个新对象,使用现有的对象来提供新创建的对象的__proto__。 (请打开浏览器控制台以查看运行结果。)
就是说参数对象obj是新创建对象obj1的构造函数的原型对象。
这里寄生组合式方法中调用方法使得子类构造函数的原型对象指向了父类构造函数的原型对象。可以理解为其中建立了__proto__这么一层关系。
注意一点,此时子类构造函数的原型对象的constructor属性是指向Parent的。
所以需要将子类构造函数原型对象的constructor重新指向子类构造函数。
ES5和ES6继承的区别
这里使用浏览器环境提供的Array方法,在Fun构造函数上使用寄生组合式继承。但是并没有实现原生Array创建数组实例对象的属性和方法。
这是为什么呢?
这是因为原生内部构造函数具有内部属性,而通过Array.apply()方法或者分配原型对象都不能在子类实例的创建过程中将this指向Array。
ES5通过构造函数创建实例的过程,是先调用子类构造函数,然后将父类属性添加到子类实例上。并且,Array对象存在不可枚举属性和不可继承的静态方法。
ES6是新建父类实例对象调用父类构造函数,再调用子类构造函数修饰this,这个this始终没有改变,并且可以相比于ES5,可以继承父类的所有行为!!
(这块细节很多,以后会单独研究后做一篇讨论)
ES6继承
ES6只有静态方法和静态属性,ES7有静态属性的提案。
这里只提一点,和Java很像,静态方法在外部通过类名调用,比不过内部是通过this调用,而且静态方法是会被继承的。
ES6存在两条继承链:一是子类构造函数的__proto__属性总是指向父类构造函数,二是子类prototype属性也指向父类的prototype属性。
ES6类的继承使用了Object.setPrototypeOf(Children.prototype, Parent.prototype),具体实现方式百度。
多态
下面说一下多态,从几个方面阐述和分析:
首先来说多态的定义:在面向对象语言中,接口的多种不同的实现方式即为多态。
一种是子类和父类可以有不同实现的”虚函数“,子类构造函数定义的函数属性或者是原型上的函数属性会覆盖父类构造函数定义的重名函数属性或者是原型上的重名函数,调用的时候根据原型链来调用。
对于比较运算符,如果是一个对象和一个是数字进行比较,则会调用对象的valueOf方法,如果valueOf方法没有指定,则会调用toString方法;如果是一个对象和一个字符串进行比较,会先尝试toString方法,然后是valueOf方法。
另外相同类的实例对象之间进行比较,会先尝试转化,再比较大小;而对非同类实例对象比较,则会直接返回false。
注:valueOf方法只能返回数字!
Javascript 继承和多态的更多相关文章
- JavaScript 继承 封装 多态实现及原理详解
面向对象的三大特性 封装 所谓封装,也就是把客观事物封装成抽象的类,并且类可以把自己的数据和方法只让可信的类或者对象操作,对不可信的进行信息隐藏.封装是面向对象的特征之一,是对象和类概念的主要特性. ...
- JavaScript 面向对象程序设计(下)——继承与多态 【转】
JavaScript 面向对象程序设计(下)--继承与多态 前面我们讨论了如何在 JavaScript 语言中实现对私有实例成员.公有实例成员.私有静态成员.公有静态成员和静态类的封装.这次我们来讨论 ...
- JavaScript 定义类的最佳写法——完整支持面向对象(封装、继承、多态),兼容所有浏览器,支持用JSDuck生成文档
作者: zyl910 [TOC] 一.缘由 由于在ES6之前,JavaScript中没有定义类(class)语法.导致大家用各种五花八门的办法来定义类,代码风格不统一.而且对于模拟面向对象的三大支柱& ...
- javascript面向对象编程,带你认识封装、继承和多态
原文链接:点我 周末的时候深入的了解了下javascript的面向对象编程思想,收获颇丰,感觉对面向对象编程有了那么一丢丢的了解了~很开森 什么是面向对象编程 先上一张图,可以对面向对象有一个大致的了 ...
- JavaScript 的继承与多态
本文先对es6发布之前javascript各种继承实现方式进行深入的分析比较,然后再介绍es6中对类继承的支持以及优缺点讨论.最后介绍了javascript面向对象编程中很少被涉及的“多态”,并提供了 ...
- 浅谈JavaScript的面向对象和它的封装、继承、多态
写在前面 既然是浅谈,就不会从原理上深度分析,只是帮助我们更好地理解... 面向对象与面向过程 面向对象和面向过程是两种不同的编程思想,刚开始接触编程的时候,我们大都是从面向过程起步的,毕竟像我一样, ...
- 2、C#面向对象:封装、继承、多态、String、集合、文件(上)
面向对象封装 一.面向对象概念 面向过程:面向的是完成一件事情的过程,强调的是完成这件事情的动作. 面向对象:找个对象帮你完成这件事情. 二.面向对象封装 把方法进行封装,隐藏实现细节,外部直接调用. ...
- JavaScript强化教程——Cocos2d-JS中JavaScript继承
javaScript语言本身没有提供类,没有其它语言的类继承机制,它的继承是通过对象的原型实现的,但这不能满足Cocos2d-JS引擎的要求.由于Cocos2d-JS引擎是从Cocos2d-x演变而来 ...
- [原创]JavaScript继承详解
原文链接:http://www.cnblogs.com/sanshi/archive/2009/07/08/1519036.html 面向对象与基于对象 几乎每个开发人员都有面向对象语言(比如C++. ...
随机推荐
- 2.7 while 、for 循环控制语句
一.while语句: 在程序中,需要重复性的做某件事: 1.1.1 while: public class Test{ public static void main(String[] args){ ...
- mysql的常用操作
基本操作 #1 操作文件夹(库) 增 create database db1 charset utf8; --指定格式为utf8 查 show databases; --查看所有的数据库 show c ...
- CSAPP HITICS 大作业 hello's P2P by zsz
摘 要 摘要是论文内容的高度概括,应具有独立性和自含性,即不阅读论文的全文,就能获得必要的信息.摘要应包括本论文的目的.主要内容.方法.成果及其理论与实际意义.摘要中不宜使用公式.结构式.图表和非公知 ...
- 赋值,什么时候用value,什么时候用innerText
赋值语句: window.document.getElementById('limittime').value='${date}' window.document.getElementById('li ...
- 加载Excel时,如何过滤空行空列
巨硬为Excel提供了丰富的C#接口,基本上可以将Excel当做一个微型数据库来用,奈何前端的我们,sql也只会写两句select * from table: 目前工作中遇到了一个问题,在需要读取的E ...
- 附录B——MySQL样例表
vendors表: 储存销售产品的供应商信息,每个供应商在这个表中有一个记录,供应商ID(vend_id)列用来匹配产品和供应商. 列名 vend_id vend_name vend_address ...
- 结合数据结构来看看Java的String类
数据结构中定义字符串是由零个或多个字符组成的有限序列,有限,指出字符串的长度是一个有限的数值:所谓的序列,说明串的相邻字符之间具有前驱和后继的关系.字符串一般记为s="a1a2...an&q ...
- maven 项目pom文件引入lib下的jar包
<dependency> <groupId>abc</groupId> <artifactId>abc</artifactId> <v ...
- 通用唯一识别码UUID
UUID 概念:UUID 是 通用唯一识别码(Universally Unique Identifier)的缩写,目前最广泛应用的UUID,是微软公司的全局唯一标识符(GUID),而其他重要的应用,则 ...
- onclick事件传递对象参数
<a href="#"onclick="editName(JSON.stringify(data).replace(/"/g, '"'))&qu ...