let与var:
1)、作用域不同:
let定义的变量是块级作用域 ;
var定义的变量是函数作用域[局部的], 但在if、for等定义的变量是全局的。
2)、在同一个作用域中同一个变量let只能声明一次,而var可以多次声明,let声明的变量可以避免全局变量被污染。
3)、var声明的变量存在变量提升,而let则没有变量提升,let声明的变量要先定义后使用。
let有暂时性死区:let声明的变量要先定义后使用。
5)、let声明的变量不会绑定到顶层对象(顶层对象可以理解为最大的全局变量,即window对象)上。
const
1、常量也是块级作用域、不存在声明提升(先定义后使用)、同一个常量只能声明一次;
2、常量一旦声明其值不能改变,但要注意:如果常量的值为数组、对象时其值是可以被改变的;(原因是数组,对象数据存放在堆区通过地址来取数据,地址并没有改变,改变的是堆区的数据。)
Symbol
是es6 新增的数据类型,和原有的数据类型(String、Number、Boolean、Object、null、undefined)一样。
格式: let s = Symbol(‘描述’);
- Symbol类型的特点:
唯一性、不能参与运算(包括字符串拼接)、for…in或for…of不能遍历
Generator
-
Generator是一个函数,在内部可以定义多个不同状态,因此generator也称为状态机,它是异步编程解决方案之一。
-
语法:
function* 函数名() {
yield 异步操作1;
yield 异步操作2;
} -
Generator特点
function 与函数名之间有一个星号
内部用yield表达式来定义不同的状态
generator函数返回的是iterator对象,而不会执行函数内部逻辑
调用next方法函数内部逻辑开始执行,遇到yield表达式停止,返回{value: yield后的表达式结果/undefined, done: false/true}
再次调用next方法会从上一次停止时的yield处开始,直到最后
yield语句返回结果通常为undefined
深拷贝与浅拷贝:
- 浅拷贝—当使用一个对象给另一对象直接赋值时 实际上是复制了引用类型的地址,导致两个对象指向同一地址的数据,只要数据修改所有对象下的数据都发生了变化
- 深拷贝—希望在不同的地址下的两个对象之间 复制属性和值
- for in的问题:
- 1只能复制对象下的第一层级的属性和值
- 2forin会将对象的原型上的属性也给复制过来
- 解决 hasOwnProperty判断该属性 是否是对象拥有的属性
1.浅拷贝
只拷贝指向某个对象的内存地址,两个对象共用一个内存空间,改变其中一个对象的值,另一个对象也跟着改变。
<script>
//简单数据类型:
let x = 33;
let y = x;
y = 66;
// console.log(x, y);
//复杂数据类型:
let obj = {
t: 11,
s: 8
};
let obj2 = obj;
obj2.s = 99;
console.log(obj, obj2);
</script>
- 深拷贝
拷贝并新创建对象,重新分配内存空间,两个对象不共用一个内存空间,改变一个对象的值不会影响另外一个对象。
<script>
//简单数据类型:
let x = 33;
let y = x;
y = 66;
// console.log(x, y);
//复杂数据类型:
let obj = {
t: 11,
s: 8,
fn: function() {
console.log('test');
}
};
let obj2 = obj;
obj2.s = 99;
console.log(obj, obj2);
//深拷贝:JSON.parse(JSON.stringify())
//注意:如果对象中的属性值为函数时则不能拷贝
let obj3 = JSON.parse(JSON.stringify(obj));
obj3.s = 100;
// console.log(obj, obj3);
let obj4 = deepCopy(obj);
console.log(obj, obj4);
//浅拷贝+递归函数:
function deepCopy(obj) {
if (Object.prototype.toString.call(obj).slice(8, -1) == 'Object') {
var result = {}
} else if (Object.prototype.toString.call(obj).slice(8, -1) == 'Array') {
var result = []
} //判断数据类型类型 如果是数组则初始一个 [] 如果是一个Object则初始一个 {}
//浅拷贝,但是+ 递归思想,就实现了深拷贝
for (var attr in obj) {
if (typeof obj[attr] == 'object') {
result[attr] = deepCopy(obj[attr])
} else {
result[attr] = obj[attr]
}
}
return result
}
</script>