目录
- 1. 基本概念(关键词 知识点)
- 2. 控制语句
- 3. 对象
- 4. 难点
- 5. 最重要的知识
- 6. 常见错误观点
- 7. JS世界的构造顺序
- 8. JS世界的构造顺序(续)
- 9. 简要的图示
- 10. 总结
1. 基本概念(关键词 知识点)§ ⇧
- 内存(图)、变量、数据类型、对象;
2. 控制语句§ ⇧
if..else...for...
3. 对象§ ⇧
- 原型(链)
- 对象分类
new一个新对象- 构造函数
this的隐式传递和显式传递(call)
4. 难点§ ⇧
- 原型
thisAJAX
5. 最重要的知识§ ⇧
5.1 JS公式§ ⇧
对象.__proto__ === 其构造函数.prototype
JS唯一公式,直接套公式
5.2 根公理Object.prototype§ ⇧
Object.prototype是所有对象的(直接或间接)原型Object.prototype的原型是null
语言设计之初即规定好的
5.3 函数公理§ ⇧
- 所有函数都是由
Function构造的 任何函数.__proto__ === Function.prototype- 任意函数包括有
Object / Array / Function
基于这三个知识和基础知识,可以推出JS世界
6. 常见错误观点 § ⇧
6.1 XXX的原型 § ⇧
- {name:‘Frank’}
- [1,2,3]
- Object
当一问到“它们的原型分别是什么?”
- 即是在问:“它们的
.__proto__是什么?” - 而不是在问:“它们的
.prototype是什么?”
正确的概念
- 「的原型」等价于「.proto」
- 中文「原型」无法区分
.__proto__和.prototype - 约定:原型默认指
.__proto__ - 只不过
.__proto__正好等于某个函数的一个属性,叫.prototype
6.2 所有对象的原型 § ⇧
矛盾点
[1,2,3]的原型是Array.prototypeObject.prototype是所有对象的原型[1,2,3]也是一种对象- 那为什么
Object.prototype不是[1,2,3]的原型
正确的概念
- 原型分两种:直接原型和间接原型
- 对于普通对象来说,
Object.prototype是直接原型 - 对于数组、函数对象来说,
Object.prototype是间接原型 - 都在原型链上
6.3 对根对象Object.prototype的质疑 § ⇧
Object.prototype不是根对象(JS公理2 说是根对象)
似是而非的推论:
Object.prototype是所有对象的原型(√)Object是Function构造出来的(√)Function构造了Object.prototype(√)Function看起来更像根对象(×)
正确的概念
Object.prototype和Object.prototype 对象的区别- 地址 和 对象的区别
- 对象里面从来不会包含另一个对象
- 对象里面只包含另一个对象对应的地址
Object.prototype = #xxx 地址
|
|
- 依据内存图,假设
Object.prototype指向一块内存#202 - 问
Object.prototype在Object里面吗?(不在) Object.prototype指向#202是一个地址#202是在内存中的对象Object.prototype只表示地址,地址在Object里面Object.prototype地址所对应的对象不在Object里面Function构造了Object.prototype的地址,假设为#303Function并未构造#303本身,即未构造根对象本身Function构造了一个存根对象地址的属性,叫Object.prototype
7. JS世界的构造顺序 § ⇧
- 创建根对象
#101(包含 toString : .. 、valueOf : .. 、proto: null) 根对象没有名字 - 创建函数的原型
#208(包含 call 、apply 、proto: #101) 没有名字 - 创建数组的原型
#404(包含 push 、 pop 、 proto: #101) 没有名字 - 创建没有名字的
Function#342(包含Function.prototype:#208) - 让
Function.prototype等于#208(有地址名字了) - 此时发现
Function的__proto__和Function都是#208(由浏览器指定Function.__proto__ === Function.prototype) - 用
Function创建Object(实际没有名字)Object.__proto__ === Function.prototype#208 - 让
Object.prototype等于#101(有地址名字了) - 用
Function创建Array(实际没有名字)Array.__proto__ === Function.prototype#208 - 让
Array.prototype等于#404(有地址名字了) - 创建
window对象(不属于JS世界) - 用
window的Object、Array属性将4 7 和 9 中的函数命名window.Function指向#2020window.Object指向#707window.Array指向#909这三个对象有名字后 根才有名字 - 记住一点,JS创建一个对象时,不会给这个对象名字
过程分析
- 1 2 3 创造原型
- 4 构造一个构造出函数的函数 Function 关联
Function.prototype - 5 让函数的原型是(创建的)函数的原型
- 6 让函数构造出的 函数的原型 也是(创建的)函数的原型
- 看起来好像是 Function 自己构造了自己,但实际只是地址相同
- 7 用 Function 构造 Object
Object._proto__ === Function.prototype - 8 Object 构造出来的对象的原型(Object自己去构造对象时 用的公有属性 #101 挂在 Object.prototype上)
- 9 用 Function 构造 Array
Array._proto__ === Function.prototype - 10 Array 构造出来的对象的原型(Array自己去构造对象时 用的公有属性 #404 挂在 Array.prototype上)
- 11 之前 都是假想的名字 没有实际的名字 创建 window 之后 将它们命名为 Function Object Array后 才有名字 它们的prototype才有名字
8. JS世界的构造顺序(续)§ ⇧
8.1 new一个构造函数§ ⇧
- 用
new Object()创建obj1 new会将obj1的原型__proto__设置为Object.prototype(假设)并指向#101(Object地址 根的地址)- 用
new Array()创建arr1 new会将arr1的原型__proto__设置为Array.prototype(假设)并指向#404(Array的地址)- 用
new Function()创建fn1 new会将fn1的原型__proto__设置为Function.prototype(假设)并指向#208(Function的地址)
new Xxx()一个x 就把x.__proto__设置为Xxx.prototype
8.2 自定义构造函数§ ⇧
- 自定义构造函数
Person函数里给this加属性 Person自动创建prototype属性 和对应的对象#502- 在
Person.prototype#502上面加属性 - 用
new Person()创建对象p new会将p的原型__proto__设为#502
9. 简要的图示§ ⇧
举例说明三个圆形、三个函数和三个对象的关系
- 三个函数:
Array函数Object函数Function函数 - 三个原型:数组的原型 对象的原型 函数的原型
- 一一对应
Object函数的prototype存储了 根(对象的原型)Function函数的prototype存储了 函数的原型Array函数的prototype存储了 数组的原型- 即 每个函数 都存储了它自己的原型
- 每个构造函数 存储了它自己的 对象的原型
- 三个函数本身的原型(
__proto__)是 函数的原型(#306) - 数组是对象,函数时对象
- 函数的构造函数构造出了函数
- 数组的构造函数构造出了数组
- 对象的构造函数构造出了对象
10. 总结§ ⇧
只能问 某物的原型是什么,单向性的问题
|
|
10.1 构造函数§ ⇧
- 是用来构造对象的
- 会预先存好对象的原型,原型的原型是根
new的时候讲对象的__proto__对象原型
10.2 对象§ ⇧
- 所有对象都直接或间接指向根对象(一层间接的原型公式上加一层
__proto__) - 如果如果对象想要分类,就在原型链上加一环
- 用构造函数可以加这一环
10.3 思考§ ⇧
- 如果加了这一环后,想再加一环
- 要用到「继承」
11. 之后学的§ ⇧
- 错误处理
try...catch.../Math/Date/正则/JSON - 网道
- 项目中深入理解
参考文章
相关文章
- 无
- 作者: Joel
- 文章链接:
- 版权声明
- 非自由转载-非商用-非衍生-保持署名
- 河 掘 思 知 简