Skip to content

警告

本文内容只在严格模式下适用

声明变量

js
var foo; //声明 foo 变量并初始化为 undefined
关键字作用域重新声明重新赋值
var全局作用域、函数作用域全局变量将作为全局对象的属性,且无法被 delete
let块级作用域
const块级作用域声明时必须指定初始值
function块级作用域声明和初始化一起优先提升
class块级作用域在类体内作为常量,无法重新赋值

变量提升

  • 把声明提升至当前作用域顶端,而不提升初始化
  • 本质是在编译阶段将变量放入内存中,也就是告诉编译器需要创建哪些变量
  • 所有变量声明的初始值为 undefined

暂时性死区

letconstclass 声明的变量,在初始化前访问会报 ReferenceError

js
(function (foo) {
    if (foo) {
        let foo = foo + 55;
        //        ^ ReferenceError
    }
    for (let foo of foo) {
        //          ^ ReferenceError
        foo;
    }
})(33);

https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Statements/let#暂时性死区

数据类型

https://tc39.es/ecma262/#sec-ecmascript-data-types-and-values

  • 原始值
    • Null
    • Undefined
    • Boolean
    • Number
    • BigInt
    • String
    • Symbol
  • Object

原型链

垃圾回收

引用计数

记录数据被引用的次数,如果没有引用则被回收。 但是无法处理循环引用的情况,因为循环引用将导致 2 个数据的引用次数至少为 1,进而无法被回收导致内存泄漏。

标记清除

定期从根对象开始,递归地查找引用的对象。把找到的对象标记为不清除,并回收找不到的对象。

代码规范

https://github.com/beginor/clean-code-javascript

闭包

柯里化

js
function curry(fn, bindArgs = []) {
    const length = fn.length;
    return function (arg) {
        newArgs = bindArgs.concat(arg);
        if (newArgs.length < length) {
            return curry.apply(this, [fn, ...newArgs]);
        } else {
            return fn.apply(this, newArgs);
        }
    };
}

WeakMap

  • WeakMap的键只能为对象
  • WeakMap对键采取弱引用,即不会影响键的垃圾回收
  • WeakMap无法对键进行迭代