来源: 个人博客

白话解释 Javascript 原型继承(prototype inheritance)

什么是继承?

学过“面向对象”的同学们是否还记得,老师整天挂在嘴边的面向对象三大特征:封装,继承,多态。今天我们就来白话一下javascript中的原型继承,没学过的同学们也不用担心,跟着往下走,我相信你会明白的。

继承,当然是面向对象其中的一种思想和概念了,所谓继承,顾名思义就是继承了。。。

比如说小明是老明唯一的儿子,老明有一个亿的资产,这一个亿的资产虽然不在小明手里,但是小明是老明儿子,小明在一定程度上“继承”了他老爸给他提供的这么多的资产,小明不仅可以享用自己赚来的钱,也可以随时消费他父辈的资产。

在程序中,其实也是类似的,如果一个对象A继承了对象B,那么对象A不仅可以使用自己的属性和方法,同时也可以使用父级B中的属性和方法。

为了能够说明白Javascript 中的原型继承,就不得不说javascript中的对象。

javascript对象两种创建(声明)方式

在javascript中你可以使用以下方式创建一个javascript 对象(object).

  1. 对象字面量(object literal)方式
  2. 构造函数(constructor)方式 // es6中可以用class创建一个真正的对象
  3. Object.create(prototype) //常用此方法进行对象间继承

第一种对象字面量方式很简单粗暴:

var a = {}; // 我创建了一个空对象a

第二种“构造函数”方式来“创建对象”。

“构造函数”只是创建一个对象的第一步!有了构造函数之后,第二部就是用它创建一个对象!

所以, 第一步,来一个构造函数,你可以把它当成一个普通函数,比如:

function People(name) {this.name = name;
}

这个函数也可以接受参数,如果大家对this关键字不了解,请先看《详解javascript this关键字》这个教程,这里我就不啰嗦了。

我们有了构造函数之后,第二步开始使用它构造一个函数。

在javascript中,我们使用 “new” 操作符 + 构造函数 来创建一个对象。

var a = new People('xiaoming');
var b = new People;

顺便提一下,如果你不想给构造函数传入参数,那么带不带括号都是一样的,也就是说:

var a = new People;
var b = new People();

这两种创建对象方式都正确。


小提示:其实第一种对象字面量方式只是构建对象的语法糖(syntax sugar),底层还是使用构造函数方式构造的:

new Object()

大家不相信的话,可以打开你的chrome的控制台,直接输入:

Object

是不是看到了下面这一行?

function Object() { [native code] }

这个Object也是个构造函数,只不过这里原生代码。

原型prototype

现在大家知道了javascript中对象创建的两种方式。

var a = {};
var xiaoming = new People();

接下来这句话请大家重复三遍:

所有的javascript对象都从一个叫“原型”的地方继承了所有的属性和方法!

这个“原型”是个啥?就是个对象!你可以把它想象成:{}。

我们前面说了创建对象的两种方法:
1, 对象字面量

var a = {};
// 其实等于
var a = new Object;

2, 构造函数

function People(){
}var a = new People();

我们说过了:

所有的javascript对象都从一个叫“原型”的地方继承了所有的属性和方法!

上面这两个例子中对象是:

a

那么原型(prototype)在哪呢?大家试着和我一样做一下:

console.log(Object.prototype);
console.log(People.prototype);

是不是都输出了一个对象?

我们之前也说了,原型(prototype)就是一个对象而已,现在大家也知道它在哪了吧?原型就是构造函数的一个属性,这里可能听着有点别扭,函数的属性?对,javascript中的构造函数也是对象!

重要的事情说三遍:javascript的原型(prototype)是什么?就是“构造函数”下的一个对象叫做“原型”(prototype)

再添一句,这个原型对象中又有个名为“constructor”的属性,指向了该函数本身。

function People(){}People.prototype.constructor === People // true

再提醒一下,原型只存在在“构造函数”中,有些同学会误解的去找一个“对象”或“对象字面量”的原型(prototype),因为我们说了原型(prototype)只存在在“构造函数”中,所以去对象或对象字面量里找原型的找不到的,只能返回undefined。比如:

var a = {};
console.log(a.prototype) // 返回undefined// 或者function People() {}
var p = new People;
console.log(p.prototype) // 依然返回undefined// 但是
console.log(People.prototype) // 就返回一个{} 当然这里面有好多原生的方法

但是,还有一个特别属性

__proto__

可以让你“向父级”查看,当前对象继承的“原型”是谁?就是孩子找爸爸。
打开你的chrome浏览器的控制台,接着上面的代码继续试验:

a.__proto__ // Object {}
p.__proto__ // Object {}
a.__proto__ === Object.prototype // true
p.__proto__ === People.prototype // true// 我们发现两个对象的原型都是对象。
// 那么我们再来看看构造函数“继承”的原型是谁?Object.__proto__ // function () {}
People.__proto__ // function () {}

看到这里,希望你能明白,不管是javascript自带的,还是我们自定义的构造函数依然继承自匿名函数的原型!(希望你没晕)

原型继承

有了上面的铺垫,我们终于能够开始说一下原型继承了。如果你上面的知识点都理解了,理解原型继承不在话下。

来个例子:

function People(name) {this.name = name;
}People.prototype.sayHi = function () {console.log('hi, my name is ', this.name);
};var a = new People('xiaoming');
a.sayHi(); // hi, my name is xiaomingvar b = new People('laoming');
b.sayHi(); // hi, my name is laoming

这种方式很简单也很直接,你在构造函数的原型上定义sayHi方法,那么用该构造函数实例化出来的对象都可以通过原型继承链访问到定义在构造函数原型上的方法。

理解了上述内容,你可以直接利用javascript的原型继承,也可以用它为基础构造自己“类”感觉小库。

来源:个人博客

白话解释 Javascript 原型继承(prototype inheritance)相关推荐

  1. 深入解析JavaScript 原型继承

    JavaScript 原型继承,学习js面向对象的朋友可以看看.十分的全面细致,具有一定的参考价值,对此有需要的朋友可以参考学习下.如有不足之处,欢迎批评指正. Object.prototype Ja ...

  2. js原型继承——prototype的使用

    文章目录 prototype的定义 原型链继承 修改prototype 继承的子类能否覆盖父类属性 总结 一些笔试题 第一题 第二题 小彩蛋 结语 参考文章 prototype的定义 javascri ...

  3. 再论JavaScript原型继承和对象继承

    JavaScript的原型继承是老生常谈.由于原型即prototype本身也是对象,所以"原型"继承可认为是一种特殊的"对象式"继承."对象式&quo ...

  4. JavaScript原型继承详细解读

    目录 1.构造函数的简单介绍 2.构造函数的缺点 3.prototype属性的作用 4.原型链(prototype chains) 5.constructor属性 5.1:constructor属性的 ...

  5. 解释下原型继承的原理。

    prototype与[[prototype]] 在有面象对象基础的前提下,来看一段代码: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 //Animal构造函数 fun ...

  6. JavaScript 原型继承

    JavaScript 中虽然有对象的概念,但它并不是一门严格意义上的面向对象编程的语言. 尽管 ES6 引入了 class 关键字,但是本质上仍然是对原型链的操作. 通过修改 JavaScript 的 ...

  7. html 原型图片,可视化的JavaScript:原型继承(动图演示)

    你是否曾思考为什么我们能使用 JS 中的一些内置属性和方法,比如 .length,.split(),.join()?我们并没有显式地声明它们,那么究竟它们从哪里来的呢? 可不要说什么"那是 ...

  8. Javascript 原型和继承(Prototypes and Inheritance)

    Javascript 原型和继承(Prototypes and Inheritance) 收藏  前面我们看到了如何使用 constructor 来初始化对象.如果这样做,那么每一个创建的新对象都会对 ...

  9. JavaScript实现继承机制(3)——通过原型链(prototype chaining)方式

    我们知道在JavaScript中定义类的原型方式,而原型链扩展了这种方式,以一种有趣的方式实现继承机制. prototype 对象是个模板,要实例化的对象都以这个模板为基础.总而言之,prototyp ...

最新文章

  1. 我与监控宝之间的点点滴滴
  2. c++11 auto 类型说明符详解
  3. 详解Framework
  4. 域名商2014年度报告:中国数据域名总量跌至22万
  5. c语言进程间通信架构,构建微服务之:微服务架构中的进程间通信
  6. 世界目光聚焦美国:埃博拉病患者是否认真是可以治愈的?
  7. C++11模板友元语法
  8. 共阳极管的代码_《手把手教你学FPGA》第三章设计实例
  9. 微信小程序demo汇总
  10. 抽象代数的人间烟火——北航李尚志
  11. U3D游戏包il2cpp逆向解包,apk加密资源解密
  12. 【电脑维修系列】妈妈再也不用担心 我装不了电脑系统 全攻略
  13. 丁仲礼院士:深入理解碳中和的基本逻辑和技术需求
  14. html中table分页显示,html中table表格分页
  15. Keras实战学习图像分类
  16. vue-giant-tree模糊搜索,自动展开匹配子节点,再次搜索可重新加载节点
  17. 微信小程序云函数安装wx-server-sdk依赖
  18. 高阶人工智能时代的畅想
  19. 助你深刻理解——最长公共子串、最长公共子序列(应该是全网数一数二的比较全面的总结了)
  20. TIFS_2013_Empirical Evaluation and New Design for Fighting Evolving Twitter Spammers

热门文章

  1. 配置Apache虚拟机
  2. java反射机制及使用案例
  3. oracle创建job权限
  4. 案例分析--AD客户端登录验证缓慢问题
  5. noise code
  6. AjaxPro无刷新选择列表框/下拉框[方便|稳定]
  7. Elasticsearch了解多少,说说你们公司es的集群架构,索引数据大小,分片有多少,以及一些调优手段 。
  8. flink streamGraph生成
  9. Vue 项目结构介绍
  10. 你真的懂ArrayList吗?说说foreach与iterator时remove的区别