JavaScript 蹭了 Java 的热度是一种弱类型动态语言早期设计用来给网页添加交互幻灯片和 DOM 编程。JS 以 ECMAScriptE 为欧洲为语言标准ES6 是 JS 的新版本2015 年发布让 JS 能够用于企业级大型项目开发。注JS 早期是一个 KPI 项目有些设计瑕疵。1. 声明变量并赋值varES5不推荐使用letES6替代varconstES6声明常量2. 作用域Scope2.1 作用域嵌套全局作用域函数局部作用域块级作用域{ ... }变量属于某个作用域JS 是弱类型变量的类型由值决定。2.2 查找变量的规则冒泡查找先在当前作用域查找找到了就使用。如果没有找到向外层作用域查找冒泡。直到全局作用域都没找到就报错ReferenceError: xxx is not defined。2.3 变量的生命周期函数或代码块执行完毕后会被垃圾回收释放内存。变量的声明会在内存中申请区域销毁时回收。3.var、let、const的区别3.1var的问题不支持块级作用域。没有常量概念只能靠代码规范约束例如var PI 3.14。存在变量提升hoisting可能违反直觉。3.2let和const支持块级作用域let声明变量值可以改变类型也可以改变但不要这么干。const声明常量声明时必须赋值简单数据类型的值不可改变复杂数据类型如对象的值可以改变但变量指向的内存地址不能改变。javascriptconst item 1; let a; // undefined // 简单数据类型 const key abc123; key ABC123; // ❌ Assignment to constant variable let points 50; points 51; points 52; // 允许但不推荐 let winner false; winner 戴; // 复杂数据类型对象 const person { name: 张三, age: 18 }; person.age; // ✅ 允许修改对象属性 person 111; // ❌ 不能重新赋值4.for循环中的var与letsetTimeout4.1 使用var不支持块级作用域循环变量i只有一个函数作用域或全局循环结束后i变成 10。所有 setTimeout 回调都引用同一个i因此打印的都是 10。javascriptfor (var i 0; i 10; i) { console.log(i); // 立即输出 0..9 setTimeout(function() { console.log(The number is ${i}); // 一秒后全部输出 10 }, 1000); }4.2 使用let支持块级作用域每次迭代都会创建一个独立的块级作用域每个i都被单独保存。setTimeout 回调引用各自作用域中的i因此打印 0..9。javascriptfor (let i 0; i 10; i) { console.log(i); setTimeout(function() { console.log(The number is ${i}); // 一秒后依次输出 0..9 }, 1000); }5. 变量提升Hoisting代码执行分为两个阶段编译阶段和执行阶段。编译阶段会准备执行上下文全局执行上下文此时用var声明的变量会被提升初始值为undefined。执行阶段才真正赋值。javascriptconsole.log(pizza); // ❌ ReferenceError: Cannot access pizza before initialization let pizza Deep Dish;注意let和const不支持变量提升在声明前访问会报错暂时性死区。变量提升是一种容易出错的设计应避免使用var始终使用let和const。6. 代码示例综合javascriptvar height 200; // 全局作用域 function setwidth() { var width 100; // 局部作用域 console.log(width, height); } setwidth(); var age 100; if (age 12) { // 块级作用域 var dog age * 7; // var 不受块级限制会泄漏到外部 let x 111; // let 只在块内有效 console.log(dog); dog; } console.log(dog); // 可以访问输出 701 // console.log(x); // ❌ x is not defined // 全局块级作用域 { const name 张三; console.log(name); } // console.log(name); // ❌ name is not defined总结特性varletconst作用域函数作用域块级块级变量提升有无无重复声明允许不允许不允许必须初始化否否是值能否改变能能简单类型不能复杂类型的属性可以最佳实践禁止使用var。默认使用const只有当变量确实需要重新赋值时才使用let。