JavaScript中的原型prototype和

问题

初学js的同学,总是搞不清楚js中的原型是什么东西,看着控制台打印出来的一串串__proto__,迷惑不已。

例如我定义一个Person,创建一个实例p,并打印实例。

function Person(){}var p = new Person();console.log(p)

图中,打印出来一个Person的实例对象p,
这个对象有个__proto__ 属性,这个是什么东西?
__proto__属性下又有constructor属性和__proto__属性。
constructor是什么,为什么打印结果是 Person()?
另外一个__proto__是什么?

为了解答上边的问题,我们需要了解一些相关概念。

一、原型

prototype

首先,说明一下,JS中,万物皆对象。

每个函数对象都有一个属性prototype(函数对象特有属性),这个属性是一个引用,指向一个对象,这个对象的作用就是包含所有实例共享的属性和方法。我们把这个对象就叫做原型对象,也叫显式原型

__proto__

每个对象都有一个属性__proto__,也可称为隐式原型,对象的隐式原型指向创建该对象的构造函数的原型(prototype)。

constructor

函数的原型对象有一个constructor属性,这个属性是一个引用,用于指向原构造函数。

关系

我们怎么理解上边的概念,而它们之间又有什么联系呢?

我们不妨打印出来p.__proto__属性:

可以看到,打印出来是一个对象,对象里边有个属性constructor。

constructor是什么呢,打印如下:

可以看到,打印出来是函数,代表的就是Person构造函数本身.

再依次打印出来Person构造函数的原型Person.prototype,
和其原型的属性constructor:

从上图我们就可以得出:

1.实例对象p有属性__proto__ 指向的就是创建它的构造函数的原型对象Person.prototype。
2.构造函数的原型对象Person.prototype的属性constructor指向Person构造函数本身。

我们可以验证一下:

但是,可能又有些同学有疑惑了,那既然所有对象都有__proto__属性,
那构造函数Person()的属性__proto__指向谁呢?
当然是指向它的构造函数的原型对象了。
函数的构造函数就是Function(),因此这里的__proto__指向Function.prototype。

那原型对象也是对象,它的__proto__属性指向谁呢?
同理,指向它的构造函数的原型对象,即Object.prototype。

这里,我们就不得不提一下,原型链的概念了。

原型链

原型链是一种机制,指的是js中,每个对象都有一个属性__proto__,指向它的构造函数的原型对象。原型对象也是一个对象,因此也有__proto__属性指向原型对象的原型对象,这样一层层向上直到对象的原型对象为空(Object的原型对象Object.prototpye的属性__proto__为null)。

因此,例子中原型链的关系如下:
p.__proto__ 指向 Person.prototype,
Person.prototype.__proto__指向的就是Object.prototype,
Object.prototpye.__proto__ 指向null

为了理解上边例子的原型链关系,我们画一张图来增加理解:

至此,上边的问题是不是心里已经有答案了呢。

总结

1.每个对象都有一个__proto__属性,指向创建它的构造函数的原型对象。
作用:构成原型链,用于实现基于原型的继承。
2.函数除了有__proto__属性,还有一个prototype属性,用来指向函数的原型对象。
作用:用于实现基于原型的继承和属性共享。
因此,你会在很多地方见到有类似这样的写法:

function Person(){}Person.prototype.hello = function(){console.log("hello")}

上边代码表示,所有Person创建的实例对象都可以共享hello方法。
3.构造函数的原型对象有属性constructor,指向构造函数本身。

PS:欢迎关注公众号:「如若清风」,一起交流学习。

(0)

相关推荐

  • 什么是原型链

    对象原型 相信大家都这样用过 map : let arr = [0, 1, 2]let doubleArr = arr.map(c => c * 2)console.log(doubleArr) ...

  • js原型原型链

    一. 普通对象与函数对象 JavaScript 中,万物皆对象!但对象也是有区别的.分为普通对象和函数对象,Object .Function 是 JS 自带的函数对象. o1 o2 o3 为普通对象, ...

  • JS的原型和继承

    __proto__ 除null和undefined,JS中的所有数据类型都有这个属性: 它表示当我们访问一个对象的某个属性时,如果该对象自身不存在该属性, 就从它的__proto__属性上继续查找,以 ...

  • JavaScript入门-对象(二)

    JavaScript对象(二) 本篇,主要讲了面向对象.this的指向问题,模拟继承过程 面向对象编程 什么面向对象编程? 编程,编程就是人们用计算机能懂的语言,告诉计算机自己想做的事情. 面向对象的 ...

  • 诚之和:如何掌握前端JavaScript中的class类

    本篇内容主要讲解"如何掌握前端JavaScript中的class类",感兴趣的朋友不妨来看看.本文介绍的方法操作简单快捷,实用性强.下面就让小编来带大家学习"如何掌握前端 ...

  • javascript中的闭包这一篇就够了

    前端技术优选 今天 以下文章来源于程序员成长指北 ,作者koala 程序员成长指北专注 Node.js 技术栈分享,从 前端 到 Node.js 再到 后端数据库,祝您成为优秀的高级 Node.js ...

  • 「知识点」JavaScript 中11个有趣的事实

    「知识点」JavaScript 中11个有趣的事实

  • 景观、符号与仪式:少数民族电影中的原型隐喻与认同建构

    张媛 电影作为特殊的大众媒介在很大程度上不仅可以作为一种历史文本的载体反映和记录社会文化与历史的发展,同时也在建构着历史叙事与集体记忆.电影中的影像承载着民族的记忆,并反映着民族的意识,通过电影影像的 ...

  • Javascript 中数据类型那些可能会中招的细节

    大迁世界 3月4日 作者:moonshinean https://moonshinean.github.io/blogs 前言 Javascript的数据类型对于大家来说一点都不默认,主要基本数据局类 ...

  • “奋战在鄂尔多斯的南京知青”照片中的原型

    [知青,这代人的生命本身就是一部传奇.难忘岁月,斑斓印痕,让历史说话,为中国知青,努力留点东西下来--] 在全国性的展览中发现自己的照片在其中,这不是每个人都能有的特大惊喜,而展览主办单位要想资料中的 ...

  • 如何在现代JavaScript中编写异步任务

    前言在本文中,我们将探讨过去异步执行的 JavaScript 的演变,以及它是怎样改变我们编写代码的方式的.我们将从最早的 Web 开发开始,一直到现代异步模式.作为编程语言, JavaScript ...

  • ​不要在 JavaScript 中使用 If-Else 和 Switch,使用对象字面量

    不要在 JavaScript 中使用 If-Else 和 Switch,使用对象字面量 WEB前端开发社区 2021-07-17 在 JavaScript 中编写复杂的条件总是有可能创建一些非常混乱的 ...

  • 他是史泰龙电影中的原型,远比梅威瑟伟大,未尝败绩却死于意外

    想必大家都看过西尔维斯特·史泰龙的电影<洛奇>,在这边电影中,史泰龙饰演了洛奇·巴尔博亚一角!在这部系列电影中,洛奇就是一位不屈不挠,坚韧不拔的拳王!而事实上,这部电影中的原型人物就是洛奇 ...

  • 泰坦尼克号中露丝原型:当年在海上死里逃生,后来过得怎样?

    "孤单不是与生俱来,而是由你爱上一个人的那一刻开始."每个人生来就是孤独的,到老也是一个人独自离去.但是,我们要承认一点,在我们面对爱情时,经常所产生的孤独感,是和爱情有关的. 这 ...