当前位置: 首页 > news >正文

原型与原型链

在JavaScript中,原型(prototype)和原型链(prototype chain)是理解对象如何继承属性和方法的关键概念。

原型

每一个对象(函数也是对象)都有一个特殊的属性叫做原型(prototype),它指向另一个对象,这个对象(构造函数.prototype)被称为原型对象, 原型对象是用来共享属性和方法的。

//构造函数:Person
function Person(name, age){this.name = namethis.age = age
}
//实例对象:obj
var obj = new Person('Jack', 26)
//原型对象:Person.prototype
Person.prototype.constructor === Person

原型对象:

        (1),原型对象有一个constructor属性指向构造函数本身(Person)。

        (2),原型对象是一个普通的对象,它包含属性和方法。

        (3),原型对象的属性和方法会被继承到所有通过原型链与它相连的对象。

//构造函数:Person
function Person(name, age){this.name = namethis.age = age
}
//实例对象:obj
var obj = new Person('Jack', 26)
//原型对象:Person.prototype
Person.prototype.constructor === Person
//原型对象也有属性和方法
Person.prototype.say = function() {console.log('hi, world!')
}
//原型对象的方法可被继承
obj.say()  //hi, world!

 隐式原型(__proto__)

 在js中,每个对象都有一个“ __proto__ ”属性(左右两边两个短下划线),这个__proto__就被称为隐式原型。

obj.__proto__ === Person.prototype //true

(1)每个js对象都有一个隐藏的原型对象属性__proto__,它指向创建它的构造函数的原型对象(Person.prototype)

(2)__proto__存在的意义在于为原型链查找提供方向,原型链查找靠的是__proto__,而不是prototype

 

原型链

按照上面所说,原型对象也应该有隐式原型。确实是的。

 (1) Person.prototype的隐式原型(__proto__)就是Object.prototype

 (2) 所有的对象,包括构造函数的原型对象,最终都继承自 Object.prototype,这是js原型链的顶点

(3)Object.prototype作为原型链的顶端,位于原型链的最末端因此,它不再有自己的原型,所以Object.prototype.__proto__ 指向null,表示原型链的终点

每个对象都有一个原型(prototype),它指向另外一个对象,而指向的对象又存在属性(_proto_)指向另外一个对象。当我们访问对象(obj)的属性时,会先在对象定义的属性中进行查找,没找到就会沿着__proto__一路向上查找,最终形成一个链式结构,这整个链式结构就叫做原型链。

        如果在原型链中找到了这个属性,就返回找到的属性值;如果整个原型链都没找到这个属性值,则返回 undefined,没找到方法直接报错(not a function)。

思考

//构造函数:Person
function Person(name, age){this.name = namethis.age = age
}
//原型对象也有属性和方法
Person.prototype.say = function() {console.log('hi, world!')
}
//原型对象也有属性和方法
Object.prototype.say = function() {console.log('oh, my god!')
}
//实例对象:obj
var obj = new Person('Jack', 26)Person.say() // ????

你觉得会输出什么。-------答案是'oh, my god!'

首先,补充个知识点。

构造函数Person的隐式原型( __proto__)指向 Function.prototype, 函数对象的__proto__指向Function.prototype,即

Person.__proto__ === Function.prototype
Function.prototype === Function.__proto__

 而且

Function.prototype.__proto__ === Object.prototype

如果在深究一点,Object也是函数对象,Object.__proto__ 也会指向Function.prototype

构造函数Person也有constructor属性,这个属性指向创建该函数的构造函数;如果自己没有定义构造函数,会指向到 Function

Person.constructor === Function

辣么,完整的原型链诞生了!

现在看图,顺便想起前文标红的句子“ 原型链查找靠的是__proto__,而不是prototype”,上述的思考题明白为什么打印'oh, my god!'了吧:

原型链从实例对象开始查找,不是从构造函数开始查找,构造函数不具备相同的原型链机制。

Person在自身没有找到say,如果要到原型对象上查找,正确的方式应该是 obj.prototype.say。

(好像很绕~)

但是,记住一点:

不要用构造函数去访问方法,尽量只使用实例去访问方法!!!

———————————————————————————————————————————

内容参考@Yi_qian1000,请移步细阅

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • 模型中间部分的卷积可视化
  • 轴承知识大全,详细介绍(附3D图纸免费下载)
  • 中秋节如何利用Python发送彩信
  • 国内外大模型汇总(包括科大星火、文心一言、通义千问、智普清言、华为大模型)
  • WPS中JS宏使用说明(持续优化...)
  • LSPosed 模块开发入门和踩的坑
  • MacBook air pro验机流程
  • STM32(一)简介
  • 【总结】CSS(SCSS) 不常用属性
  • 【高级编程】实用类详解(下)万字整理Java时间日期类 JDK8新日期
  • c++ linux——进程共享内存
  • 《JavaEE进阶》----3.<SpringBoot项目创建细节大全+打jar包运行>
  • 若依框架登录鉴权详解(动态路由)
  • 鸿蒙轻内核M核源码分析系列四 中断Hwi
  • Spring Boot 整合 Sentinel 实现流量控制
  • 【402天】跃迁之路——程序员高效学习方法论探索系列(实验阶段159-2018.03.14)...
  • Android Volley源码解析
  • AngularJS指令开发(1)——参数详解
  • CNN 在图像分割中的简史:从 R-CNN 到 Mask R-CNN
  • Django 博客开发教程 8 - 博客文章详情页
  • Docker 笔记(2):Dockerfile
  • eclipse(luna)创建web工程
  • EventListener原理
  • java取消线程实例
  • Java知识点总结(JavaIO-打印流)
  • Linux后台研发超实用命令总结
  • mysql外键的使用
  • npx命令介绍
  • SegmentFault 社区上线小程序开发频道,助力小程序开发者生态
  • Webpack 4x 之路 ( 四 )
  • 笨办法学C 练习34:动态数组
  • 大整数乘法-表格法
  • 给新手的新浪微博 SDK 集成教程【一】
  • 关于List、List?、ListObject的区别
  • 基于 Babel 的 npm 包最小化设置
  • 类orAPI - 收藏集 - 掘金
  • 双管齐下,VMware的容器新战略
  • 我是如何设计 Upload 上传组件的
  • 一起来学SpringBoot | 第十篇:使用Spring Cache集成Redis
  • puppet连载22:define用法
  • (20)目标检测算法之YOLOv5计算预选框、详解anchor计算
  • (70min)字节暑假实习二面(已挂)
  • (pojstep1.1.1)poj 1298(直叙式模拟)
  • (翻译)Quartz官方教程——第一课:Quartz入门
  • (十二)springboot实战——SSE服务推送事件案例实现
  • (一)u-boot-nand.bin的下载
  • (一)认识微服务
  • (转)母版页和相对路径
  • (转)全文检索技术学习(三)——Lucene支持中文分词
  • (自适应手机端)行业协会机构网站模板
  • **python多态
  • .htaccess配置重写url引擎
  • .NET Core、DNX、DNU、DNVM、MVC6学习资料
  • .NET DataGridView数据绑定说明
  • .NET/C# 使用 ConditionalWeakTable 附加字段(CLR 版本的附加属性,也可用用来当作弱引用字典 WeakDictionary)