资讯专栏INFORMATION COLUMN

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

kid143 / 2799人阅读

摘要:我们有了构造函数之后,第二步开始使用它构造一个函数。来个例子这种方式很简单也很直接,你在构造函数的原型上定义方法,那么用该构造函数实例化出来的对象都可以通过原型继承链访问到定义在构造函数原型上的方法。

来源: 个人博客
白话解释 Javascript 原型继承(prototype inheritance) 什么是继承?

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

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

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

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

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

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

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

对象字面量(object literal)方式

构造函数(constructor)方式 // es6中可以用class创建一个真正的对象

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 xiaoming

var b = new People("laoming");
b.sayHi(); // hi, my name is laoming

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

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

来源:个人博客

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/88118.html

相关文章

  • 白话原型原型

    摘要:二原型和原型链其实,原型这个名字本身就很容易产生误解,原型在百度词条中的释义是指原来的类型或模型。对象的原型是通过创建的对象,其原型是而的原型是,从而两个原型对象和有了继承关系三和这是容易混淆的两个属性。 关于原型和原型链的介绍,网上数不胜数,但能讲清楚这两个概念的很少,大多数都是介绍各种对象、属性之间如何指来指去,最后的结果就是箭头满天飞,大脑一团糟。本文将从这两个概念的命名入手,用...

    lijy91 评论0 收藏0
  • 深入理解JavaScript

    摘要:深入之继承的多种方式和优缺点深入系列第十五篇,讲解各种继承方式和优缺点。对于解释型语言例如来说,通过词法分析语法分析语法树,就可以开始解释执行了。 JavaScript深入之继承的多种方式和优缺点 JavaScript深入系列第十五篇,讲解JavaScript各种继承方式和优缺点。 写在前面 本文讲解JavaScript各种继承方式和优缺点。 但是注意: 这篇文章更像是笔记,哎,再让我...

    myeveryheart 评论0 收藏0
  • 面向对象的 JavaScript

    摘要:是完全的面向对象语言,它们通过类的形式组织函数和变量,使之不能脱离对象存在。而在基于原型的面向对象方式中,对象则是依靠构造器利用原型构造出来的。 JavaScript 函数式脚本语言特性以及其看似随意的编写风格,导致长期以来人们对这一门语言的误解,即认为 JavaScript 不是一门面向对象的语言,或者只是部分具备一些面向对象的特征。本文将回归面向对象本意,从对语言感悟的角度阐述为什...

    novo 评论0 收藏0
  • JavaScript中的面向对象(object-oriented)编程

    摘要:对象在中,除了数字字符串布尔值这几个简单类型外,其他的都是对象。那么在函数对象中,这两个属性的有什么区别呢表示该函数对象的原型表示使用来执行该函数时这种函数一般成为构造函数,后面会讲解,新创建的对象的原型。这时的函数通常称为构造函数。。 本文原发于我的个人博客,经多次修改后发到sf上。本文仍在不断修改中,最新版请访问个人博客。 最近工作一直在用nodejs做开发,有了nodejs,...

    JerryZou 评论0 收藏0
  • 理解JavaScript的核心知识点:原型

    摘要:首先,需要来理清一些基础的计算机编程概念编程哲学与设计模式计算机编程理念源自于对现实抽象的哲学思考,面向对象编程是其一种思维方式,与它并驾齐驱的是另外两种思路过程式和函数式编程。 JavaScript 中的原型机制一直以来都被众多开发者(包括本人)低估甚至忽视了,这是因为绝大多数人没有想要深刻理解这个机制的内涵,以及越来越多的开发者缺乏计算机编程相关的基础知识。对于这样的开发者来说 J...

    iKcamp 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<