20200828 王维

学习总结

1.函数重载

相同函数名,不同参数列表的多个函数,在调用时,根据传入参数的不同,自动选择匹配的函数执行

减少API的数量,减轻调用者的负担

只要一项任务,需要根据不同的参数,执行不同的操作时,就需要使用重载

虽然 JS语法不支持重载,JS中不允许多个同名函数同时存在,但是JS内置arguments对象接受所有传入函数的参数值,可以通过判断arguments的元素个数执行不同的操作。arguments在函数调用时自动创建,是一个类数组对象(长得像数组的对象)。

类数组对象与数组异同

同:拥有下标,长度,可以通过for in/for of遍历

不同:类型不同,类数组对象无法调用数组的API

2.作用域

全局作用域优缺点

优点:可以反复使用

缺点:随处可用,容易造成全局污染,建议尽量少用全局变量

函数作用域优缺点

优点:仅函数内可用,不会被污染

缺点:不可重用

3.函数生命周期

开始执行程序前
创建ECS
首先在ECS中添加浏览器主程序的执行环境main
创建全局作用域对象window,所有全局变量都是保存在window对象中
main执行环境引用window

定义函数时
用函数名声明全局变量
创建函数对象,封装函数定义
函数对象的scope属性,指回函数创建时的作用域
函数名变量引用函数对象

调用函数时
向ECS中压入本次函数调用的执行环境元素
创建本次函数调用时使用的函数作用域对象(AO)
在AO中创建所有局部变量
包含
1. 形参变量
2. 函数内用var声明的变量
设置AO的parent属性引用函数的scope属性指向的父级作用域对象
函数的执行环境引用AO
变量的使用顺序

调用后
函数的执行环境出栈,导致AO释放,同时导致AO中的局部变量一同被释放

作用域链(scope chain)

各级作用域逐级引用,形成的链式结构,保存着所有的变量,控制着变量的使用顺序。

作用域链创建规则,当定义一个函数时(注意,是定义的时候就开始了),它实际上保存一个作用域链。当调用这个函数时,它创建一个新的对象来储存它的参数或局部变量,并将这个对象添加保存至那个作用域链上,同时创建一个新的更长的表示函数调用作用域的“链”。

4.闭包

重用变量,又保护变量不被污染的机制

闭包三步:

外层函数 包裹受保护的变量和操作变量的内层函数

外层函数要返回内层函数的对象

调用外层函数,用外部变量接住返回的内层函数对象,形成闭包

闭包的形成:

外层函数调用后,外层函数的作用域对象(AO),无法释放,被内层函数对象的scope引用着

闭包缺点:

比普通函数占用更多内存,多的是外层函数的作用域对象(AO)始终存在

容易造成内存泄漏

释放闭包:

将引用内层函数对象的外部变量置为null,导致内层函数对象被释放,导致外层函数的AO被释放

注意:同一次外层函数调用,返回的内层函数对象,共用同一个受保护的变量

心得体会

今天学习了比较困难的内容和很多概念性的内容,困难的逻辑的知识需要自己多看不同例子,准确理解他的定义和作用,概念性的东西就需要自己多记忆。

评论