JavaScript - Function
闭包
闭包是一个
绑定了执行环境的函数,JavaScript 中的函数完全符合闭包的定义
在 JavaScript 中,与
闭包对应的概念就是函数
执行上下文
- 执行上下文:
执行一段代码(包括函数),所需要的所有信息 - 相比于普通函数,
JavaScript 函数的主要复杂性来源于其携带的环境部分
版本
ES3
| Key | Desc |
|---|---|
scope |
作用域、作用域链 |
variable object |
变量对象,用于存储变量的对象 |
this value |
this 值 |
ES5
| Key | Desc |
|---|---|
lexical environment |
词法环境,当获取变量时使用 |
variable environment |
变量环境,当声明变量时使用 |
this value |
this 值 |
ES2018 - Recommend
this value被纳入lexical environment
| Key | Desc |
|---|---|
lexical environment |
词法环境,当获取变量或者 this 值时使用 |
variable environment |
变量环境,当声明变量时使用 |
code evaluation state |
用于恢复代码执行位置 |
Function |
执行的任务是函数时使用,表示正在被执行的函数 |
ScriptOrModule |
执行的任务是脚本或者模块时使用,表示正在被执行的代码 |
Realm |
使用的基础库和内置对象实例 |
Generator |
仅生成器上下文有这个属性,表示当前生成器 |
var
通过创建一个函数,并且
立即执行,来构造一个新的域,从而控制var的范围
使用
()
1 | (function () { |
使用
void- 推荐
有效避免了语法问题,并且void在语义上表示忽略后面表达式的值,变成undefined
1 | void function () { |
声明的变量与被赋值的变量可能会
不一致,要借助with(不推荐使用)
1 | var b; |
let
从
ES6开始引入let,JavaScript 在运行时引入了块级作用域
在let之前,JavaScript 的if、for等语句都不产生作用域
forifswitchtry/catch/finally
函数
切换执行上下文的主要场景:函数调用
普通函数
使用
function关键字定义的函数
1 | function foo() { |
箭头函数
使用
=>运算符定义的函数
1 | let foo = () => console.log("hello js"); |
方法
在
class中定义的函数
1 | class Human { |
生成器函数
使用
function*定义的函数
1 | function* generator(i) { |
类
使用
class定义的类,实际上也是函数
1 | class Human { |
异步函数
在
普通函数、箭头函数和生成器函数加上async关键字
1 | async function f1() { |
this
行为
this是执行上下文中很重要的一个组成部分,同一个函数调用方式不同,得到的this也不同
1 | function showThis() { |
普通函数的this由调用它所使用的引用决定的- 获取
函数的表达式,实际上返回的并非函数本身,而是一个Reference类型Reference类型的组成:一个对象+一个属性值Reference类型中的对象被当作this值,传入到执行函数时的上下文当中
调用函数时使用的引用,决定了函数执行时刻的 this 值- 从
运行时角度来看,this 与 OOP 毫无关联,而是与函数调用时使用的表达式有关
如果使用
箭头函数,不论用什么引用来调用它,都不会影响this值
1 | let showThis = () => console.log(this); |
方法
1 | class C { |
机制
TBD
All articles on this blog are licensed under CC BY-NC-SA 4.0 unless otherwise stated.











