| |
|
开发:
C++知识库
Java知识库
JavaScript
Python
PHP知识库
人工智能
区块链
大数据
移动开发
嵌入式
开发工具
数据结构与算法
开发测试
游戏开发
网络协议
系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程 数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁 |
-> JavaScript知识库 -> JS原型链的学习总结 -> 正文阅读 |
|
[JavaScript知识库]JS原型链的学习总结 |
关于原型链的学习总是很迷,看了过段时间就忘,或者不理解,看多了就走火入魔了 这次换个思路来学习,先搞懂JavaScript中的Object和Function的关系、源头 (假设你已经看了很多关于原型链的文章和各种眼花缭乱的图...) 1.Object 首先打印下Object,可以看到Object是个function Ojbect(){...},打印它的内部结构里面有很多属性,其中有个prototype(原型),后面有用 新建一个对象let?a={},其实就是let?a=new Object(),普通对象a就是构造函数Object的实例化 打印一下a的内部结构,可以看到a内部有个__proto__属性,里面有构造方法和toString等方法 我再打印下Object.prototype,发现和a里面的__proto__长得一样,那是不是一样呢,试一下 发现果然一样,也就是说a的__proto__指向了函数Object的prototype 再新建一个let b={},试试看a和b的__proto是否相等 ? 发现也是相等,也就是a和b的__proto__都指向函数Object的prototype,在内存中是同一块空间 为什么这么做呢,试想如果没有这个功能,a和b如果想用toString方法,需要a b分别.toString=function(){...},分别在内存中开辟一块空间,打个比方,内存分成100份且只有100份,每个对象的toString方法占1份,100个就占完了内存,所以JS作者把对象需要共享的属性和方法,放到一个内存空间里,每一个对象都有一个属性都指向这个空间,节省资源。 那么Object的prototype指向谁呢,试一下 是null,这个不太好理解,可以理解为到此为止了,不要继续往上找了,万物起源皆有源头,就到这吧。 总结下,就是普通对象的__proto__指向Object.prototype,我们只是通过控制台打印去佐证了这一点,先记住吧,js作者是这么设计的,就像1+1=2。 暂且理解为 第一条结论:普通对象最终继承自Object.prototype,Object.prototype直接继承自根源对象null 2.Function 我们需要去搞懂Object和Function的关系,在这之前先记住 【1】只有函数对象有prototype,就像上面的Object里有prototype和__proto__,而普通对象a中没有prototype,只有__proto__ 【2】prototype里存储的是原型,留着继承给下一级的,而下一级的__proto__指向上一级的prototype 打印Function,发现Function.prototype.__proto__和Object.prototype长得也一样,一打印果然是true,也指向Object.prototype 暂且得出第二条结论?Function.prototype最终继承自Object.prototype 马上进入最绕的部分 Object是函数,它的__proto__指向上一级的原型,也就是Function.prototype,Object继承自Function.prototype,这很好理解 Function继承自谁,它的上一级是谁,Function的__proto__指向谁,答案是Function.prototype,Function自己的原型...这就有点无解了,你要问为什么,只能问JS作者了 打印出来可以看到里面是常见的apply call bind等方法 结合上面得出的第二条结论 Function.prototype最终继承自Object.prototype 得出第三条结论 一切函数对象都继承自Function.prototype(且Function.prototype会最终继承自Object.prototype) 像Object Array和Function本身都继承自Function.prototype,那Function是大王了吗,结果Function.prototype又继承自Object.prototype,这属实是互相继承...最绕的就是这一块了。 ---------------------------------------------------------------------------------------------------------------------------- 现在再去看这张很常见的眼花缭乱的图中的红框部分就好理解了 1.Object和Function,这两个谁是大王谁是小王? 2.Object是函数,__proto__指向它的上一级Function.prototype 3.Function也是函数,__proto__指向它自身Function.prototype,可以说Function就是函数中的大王,任何构造函数都是Function的实例 4.Function.prototype.__proto__指向Obect.prototype,所以任何对象,不论是普通对象还是函数对象都是Object的实例 5.Object.prototype.__proto__最终指向null 6.同一个对象的__proto__属性和prototype属性是没有关联的,除了Function。prototype对自身是不可见的,它的作用是留着继承给后代,而__proto__的作用是引用上一级的 prototype 对象 7.我认为Object.prototype就像一个辅助,它的原型中提供一些普通对象要用到的方法,如toString,valueOf,hasOwnProperty等,它的指针指向null,另外它的存在还使得Function.prototype可以指向它,以及所有的prototype通过原型链都指向它,最终指向null,而Function更偏向于实战,在js世界中发挥巨大作用,从它演化出Function Object Array Number String等,再去衍生js中的万物,不好说谁是大小王。 至于上面那个图中其他的知识点,比较好理解了 let o1,o2=new Object(),普通对象o1 o2的__proto__指向Object.prototype function Foo(),let f1,f2=new Foo(),f1,f2的__proto__指向Foo.prototype,这里Foo.prototype是普通对象,结合第一条结论,普通对象指向Object.prototype,最终指向null Foo.__proto__指向父级函数Function.prototype,再结合第三条结论,指向Object.prototype,最终指向null Foo的原型链不同于f1 f2,这里容易混淆,需要分清楚,但是最终殊途同归... 还有一个知识点就是原型的构造函数指向,原型中的构造函数指向函数本身 实例化一个Person叫p,p的构造函数也指向这个函数本身 ? 所以,其实可以理解成原型上的构造函数也是Person的一个实例化 同理Object的prototype上的构造函数指向Object Function的prototype上的构造函数指向Function 再来一张图,如果能看懂,就差不多了 思考题: Object.prototype.toString和Object.toString是一回事吗? 最后,说一下__proto__这个属性,是隐示属性,在有的浏览器中它不是__proto__而是[[Prototype]],具体可以去了解下区别,下面截图是IE的Edge浏览器 补充 基本数据类型,Boolean String Number的坑,直接赋值,虽然proto指向了Boolean的prototype,但是用instanceof却是false...后续补充 ? ----暂时到这,很晕---- 后续可以去看下call apply bind,还有instanceof 如何实现,对原型链的理解会有帮助 以及上面截图中[[Scopes]],等到闭包那一块那去写这个 |
|
JavaScript知识库 最新文章 |
ES6的相关知识点 |
react 函数式组件 & react其他一些总结 |
Vue基础超详细 |
前端JS也可以连点成线(Vue中运用 AntVG6) |
Vue事件处理的基本使用 |
Vue后台项目的记录 (一) |
前后端分离vue跨域,devServer配置proxy代理 |
TypeScript |
初识vuex |
vue项目安装包指令收集 |
|
上一篇文章 下一篇文章 查看所有文章 |
|
开发:
C++知识库
Java知识库
JavaScript
Python
PHP知识库
人工智能
区块链
大数据
移动开发
嵌入式
开发工具
数据结构与算法
开发测试
游戏开发
网络协议
系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程 数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁 |
360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年12日历 | -2024/12/27 20:52:31- |
|
网站联系: qq:121756557 email:121756557@qq.com IT数码 |
数据统计 |