ES6笔记(一)

198 阅读11分钟

ES6 笔记(一)

一 :关键字扩展

1:块级作用域

  • 块作用域由{}包括,if语句和for语句中{}也属于块作用域,块内使用let声明的变量,只会在当前块内有效。
  • 块级作用域可以任意嵌套。
  • 使用块级作用域可以防止全局变量污染。
{ //块级作用域  } 
同:
(function(){...})()
  • 建议函数在顶层作用域和函数作用域中声明,尽量避免在块级作用域中声明,如有需要,应写为函数表达式方式。

2:let关键字

let声明的变量,只在命令所在代码块内生效,即增加了块级作用域。

特点:

  • let命令不存在变量提升
  • 不允许重复声明
  • 块级作用域出现,立即执行函数不再需要
  • 不影响作用域链
  • 不再是顶层全局对象的属性

3:const关键字

const声明必须赋初始值;声明一个只读变量,声明后不允许改变;值不允许修改。

const 保证变量指向的内存地址不允许变动

**特点:**同let。

二:变量的解构赋值

解构赋值本质就是赋值:把结构解散重构然后赋值,是对赋值运算符=的一种扩展。

赋值语法:

解构的目标 = 解构源

解构目标:定义的常量或变量

解构源:待解构的数组或对象

1:对象解构赋值

{
    const {a,b,c} = {a:1,b:2,c:3};
    console.log(a,b,c) //1,2,3
}

顺序不用一一对应;= 右侧可以是一个由对象赋值的常量或变量

  • 嵌套对象解构
const {a,b,c:{d,e}} = {a:1,b:1,c:{d:2,e:2}};
console.log(a,b,d,e) // 1,1,2,2
  • 可忽略解构源的属性
const{a,b} = {a:1,b:2,c:3,d:4};
console.log(a,b); // 1,2
  • 剩余运算符
const {a,...b} = {a:1,b:2,c:3,d:4};
console.log(b);  //{b: 2, c: 3, d: 4}
  • 不完全结构
const {a,b,c,d} = {a:1,b:1};
console.log(a,b,c,d); // 1,1,undefined,undefined
  • 解构默认值
const {a,b = 1} = {a:1};
consloe.log(a,b) //1,1
const {a,b = 1} = {a:1,b:2};
console.log(a,b) //1,2
  • 函数传参数
function fn({a,b,c}) {console.log(a,b,c)};
fn({a:1,b:2,c:3}) //1,2,3
  • 解构赋值时,如等号右侧为undefined或null会报异常

2:数组解构赋值

  • 基本语法
let [a,b,c,d] = [1,2,3,4];
console.log(a,b,c,d); //1,2,3,4
  • 忽略元素
let [,,,d] = [1,2,3,4];
console.log(d);
  • 赋值上下文
let a = 100;
let b = 100;
[a,b] = [1,2];
console.log(a,b); //1,2
  • 变量交换
let a = 1;
let b = 2;
[a,b] = [b,a];
console.log(a,b); //2,1
  • 默认值
let [a,b,c,d] = [1,2,3];
console.log(a,b,c,d); //1,2,3,undefined
  • 嵌套数组结构
let [a,b,c,d] = [1,2,[3,42]];
console.log(a,b,c,d); //1,2,[3,42]
  • 不定元素
let [a,...arg] = [1,2,3,4];
console.log(a,arg); //1,[2,3,4]
  • 数组复制
let arr = [1,2];
let arr2 = [3,4];
let arr3 = [...arr,...arr2];
console.log(arr3);

3:函数解构赋值

function fn(a,{username,age},b) {
            console.log(a,username,age,b);
        }
fn(1,{username:'zs',age:10},2); //1,zs,10,2
fn(1,2,{username:'zs',age:10}); 
//1 undefined undefined {username: 'zhang', age: 12}
  • 如果调用函数时不提供被解构的参数会导致抛出错误
function fn(a,b) {}
fn();
//TypeError: Cannot destructure property 'a' of 'undefined' as it is undefined.
function fn([a,b]) {}
fn();
//TypeError: undefined is not iterable (cannot read property Symbol(Symbol.iterator))
  • 可以为解构参数指定默认值
function fn({a=1,b=1}={}) {
    console.log(a,b) 
}
fn()//1,1
  • 解构返回结果
function fn() {
    return {
        data: '返回结果'
    }
}
let {data} = fn();
console.log(data); //返回结果

4 :字符串解构

let str = 'abcde';
let [a,b,c] = str;
consloe.log(a,b,c); 

5:数值和布尔值解构

  • 解构赋值时,如果等号右边是数值和布尔值,则会先转化为对象
let {toString: s} = 123;
console.log(s === Number.prototype.toString); // true
let {toString: b} = true;
console.log(b === Boolean.prototype.toString); //true

三:字符串拓展

1:模板字符串

  • 模板字符串(template string),是增强版的字符串,用反引号(`)标识,可以嵌套变量,可以换行,可以包含单引号和双引号。
let a = 'abc';
let str = `${a}`;
console.log(str); //abc
  • 大括号中可以放任意js表达式,可以进行运算,调用函数,以及引用对象属性
let fn = function () {
      return 1;
}
let arr = [1,2,3];
let str = `${fn()}+${arr[1] + arr[0]}`;
console.log(str); //1+3

2:字符串新增方法

  • 去空格

trim():删除字符串两端空白符

trimStart():去除首部的空格

trimEnd():去除尾部的空格

  • 判断

startsWith():判断开头有没有包含某个字符串

endsWith():判断结尾有没有包含某个字符串

includes():判断开头有没有包含某个字符串

let str = 'abcdefg';
console.log(str.startsWith('a')); //true
console.log(str.endsWith('a'));	//false
console.log(str.includes('a')); //true
  • repeat():重复当前字符串,指定次数
let str = 'abc';
console.log(str.repeat(2)); //abcabc
  • 补充字符

padStrat():在前边补充任意字符,达到指定长度,第一个参数为指定长度,第二个参数为补充字符

padStrat():在后边补充任意字符,达到指定长度,第一个参数为指定长度,第二个参数为补充字符

let str = 'abc';
console.log(str.padStart(5,'o'));  //ooabc
console.log(str.padEnd(5,'o')); //abcoo

四:spread运算符与rest参数

1:spread运算符

  • 复制,合并数组
let arr = [1,2];
let arr1 = [...arr]; //[1,2]
console.log(arr1);
let arr2 = [3,4];
let arr3 = [...arr,...arr2];
console.log(arr3); //[1,2,3,4]
  • 复制,合并对象
let obj = {
     a: 1,
     b: 2
  };
let obj2 = {
   ...obj
   };
console.log(obj2, obj2 === obj); //{a:1,b:2}
let obj3 = {
    c: 3,
    d: 4
  };
let obj4 = {
    ...obj,
    ...obj3
  };
 console.log(obj4); //{a: 1, b: 2, c: 3, d: 4}
  • 字符串转为数组
let str = 'wow';
let [...str1] = str;
console.log(str1);  //['w', 'o', 'w']
  • 伪数组转为真数组
function fn() {
    let [...arg] = arguments;
    console.log(arg);
  }
fn(1,2,3,4) //[1, 2, 3, 4]

2:rest参数

  • 获取函数调用时传入的参数
function fn(...arg) {
    console.log(arg);
  }
fn(1,2,3,4); //[1,2,3,4]
  • 和普通函数混合使用时,需要放在参数后面
function fn(a,...arg) {
    console.log(arg);
  }
fn(1,2,3,4); //[2,3,4]
  • 函数的length属性,不包含rest参数
function fn(a,b,c,...arg){};
console.log(fn.length); //3

五:数组的拓展

1:Array对象的新方法

  • from:把伪数组转为数组(可以使用数组的方法)
function fn() {
    console.log(Array.from(arguments));
}
fn(1,2,3); //[1,2,3]
  • of:弥补构造函数Array()的不足,指定数组元素
console.log(Array());    //[]
console.log(Array(2));   //[empty × 2]
console.log(Array(1,2)); //[1, 2]
console.log(Array.of(2)); //[2]

2:Array原型上新增方法

  • copyWithin():在当前数组内部,将指定位置的成员复制到其他位置(会覆盖原有成员),然后返回当前数组,保证数组长度不变
//它接三个参数:
//target:从该位置开始替换数据,如果为负值,表示倒数
//start:从该位置开始读取数据,默认值为0,负值为末尾开始计算
//end:到该位置前停止读取数据,默认为数组长度,负值为末尾开始计算
let arr = [1,2,3,4];
let arr2 = arr.copyWithin(1,0,3); //[1, 1, 2, 3]
  • fill():使用固定值填充数组,数组中已有的元素,会被抹去
//可接受第二个和第三个参数,用于指定起始位置和结束位置
let arr = [1,2,3];
console.log(arr.fill('a'));  //['a','a','a']
let arr = [1,2,3];
console.log(arr.fill('a',2,3)); //[1,2,'a']
  • entries():对键值对的遍历,keys():对键名的遍历,values():对键值的遍历
let arr = [1,2,3];
for(let [key,values] of arr.entries()) {
    console.log(key,values);  
} //0 1 1 2 2 3
for(let key of arr.keys()){
    console.log(key);
} //0,1,2
for(let values of arr.values()){
     console.log(values);
}//1,2,3
  • find():找出第一个符合条件的数组成员,findIndex():找出符合条件的第一个元素的下标,没有则得到-1
let arr = ['a','b','c'];
let res = arr.find(function (item) {
    return item = 'a';
})
console.log(res); //a
let res1 = arr.findIndex(function (item) {
   return item = 'a';
})
console.log(res1); //0
  • includes():返回布尔值,表示某个数组中是否包含给定的值
let arr = [1,2,3];
console.log(arr.includes(1)); //true
  • flat():将嵌套数组拉平,返回新数组,对原数组没有影响
let arr = [1,2,3,[4,5,[6,7]]]
console.log(arr.flat()); //[1,2,3,4,5[6,7]]
console.log(arr.flat(Infinity));//[1,2,3,4,5,6,7]

六:函数拓展

1:函数参数设置默认值

function fn(a=1) {
    console.log(a);
}
fn(); //1

2:箭头函数

① 箭头函数

const fn = () =>{
            
}
//参数为一个参数时,且返回值为一条语句时
const fn1 = a => a;

当对参数进行解构时,括号不允许省略;

没有参数或者多个参数时,参数括号不能省略;

当函数体为多条语句时,花括号不能省略;

函数体内只有一行代码,该代码返回为对象,可用圆括号将其包裹

② 注意事项

  • 箭头函数没有自己的this,箭头函数内部的this并不是调用时指向的对象,而是定义时指向的对象
  • 箭头函数不能用于构造函数,不能使用new关键字调用
  • 箭头函数没有arguments对象
  • 箭头函数使用call,apply,bind无法改变this指向

七:对象的拓展

1:对象简写

//将变量的名字作为属性名,变量属性值作为属性值
function fn(username) {
     var obj = {
       username,
}
     console.log(obj); //{username: 'zs'}
   }
fn('zs');

function fn(username) {
      var obj = {
        [username]:'ll'
}
 	console.log(obj);  //{zs: 'll'}
   }
fn('zs');

2:属性名表达式

利用函数返回值作为属性名表达式

function fn() {
   return 'foo';
}
const obj = {
   [fn()]:10
}
console.log(obj); //{foo: 10}

3:对象新增方法

// Object.is():比较两个值是否相等
console.log(Object.is({},{}));  //fasle
console.log(Object.is('foo','foo')); //true
console.log(Object.is(NaN,NaN)); //true

// Object.assign():对象的合并,将源对象复制到目标对象,返回目标对象
const target = {a:1,b:2};
const source = {c:1,d:2};
console.log(Object.assign(target,source));//{a: 1, b: 2, c: 1, d:2}

// Object.keys():返回一个成员是对象键名的数组
console.log(Object.keys({a:1,b:2})); //[a,b]
// Object.values():返回一个成员是对象键值的数组
console.log(Object.keys({a:1,b:2})); //[1,2]
// Object.entires():返回一个成员是对象键值对的数组
console.log(Object.entries({a:1,b:2})); // [[a:1],[b:2]]

八:Math的拓展

1:进制写法

二进制用ob表示;八进制用0o表示

2:新增方法

  • Math.pow():指数运算,表示一个值的n次方

  • Math.trunc():将数字的小数部分去掉,保留整数

  • Math.sign():判断一个数字的性质,正数为1,负数为-1,NaN为NaN

  • Math.sqrt():平方根

  • Math.cbrt():立方根

  • Math.hypot():求所有参数平方和的立方根

九:Number的扩展

1:新增方法

  • Number.isFinite():用来检查一个数是否为有限值,返回值为布尔值,传入非数值,会返回false,Infinity会返回fasle
  • Number.isNaN():判断是否为NaN,返回布尔值
  • Number.isInteger():判断是否为整数
  • Number.parseInt(str):将字符串转换为对应数值

十:新增数据类型

1:Symbol

原始数据类型,表示独一无二的值

const s1 = Symbol('i am symbol');
console.log(s1); //Symbol(i am symbol)
//用于对象属性名
const obj = {
     a: 1,
    [Symbol()]: 2
}
console.log(obj); //{a: 1, Symbol(): 2}
//对一无二
const s = Symbol();
const ss = Symbol();
console.log(s === ss); //false
//相等时
const s2 = Symbol.for();
const s3 = Symbol.for();
console.log(s2 === s3); //true

特点:

  • Symbol中传入的字符串没有任何意义,只是用来描述
  • Symbol不能使用New调用
  • 不能用Number转换,不允许运算
  • Symbol作为对象属性或方法时,需提前用变量存储,否则,无法访问该属性或方法
  • 无法使用for in遍历,可用使用Object.getOwnPropertySymbols
const obj = {
     a: 1,
     [Symbol('s')]: 2,
     [Symbol('ss')]: 3
}
console.log(Object.getOwnPropertySymbols(obj));
//[Symbol(s),Symbol(ss)]

2:BigInt

Javascript所有数字保存为64位浮点数,数值的精度只能到53个二进制位(相当于16个十进制),大于这个范围的数,无法精确表示。BigInt只表示整数,没有位数限制,任何位数的整数都可以精确表示

let numN = 123n;
console.log(typeof numN);// "bigint"

BigInt与普通整数是两种值,它们之间并不全等

let num = 10;
let numN = 10n;
console.log(num == numN); //true
console.log(num === numN); //false

十一:新增数据结构

1:Set

类似数组,但是成员都是唯一的,没有重复的值;接受一个数组,或者具有iterable接口的其他数据结构,作为参数,用来初始化

const s = new Set([1,2,3,4]);
console.log(s); //{1, 2, 3, 4}

属性方法:

  • size:返回Set的长度
  • add():添加某个值,返回Set结构本身
  • delete:删除某个值,返回布尔值,表示是否删除成功
  • has():返回布尔值,表示该值是否为Set的成员
  • clear():清除所有成员
  • keys():返回键名,Set结构没有键名,只有键值,或为同一值
  • values():返回键值
  • entries():返回键值对
  • forEach():使用回调函数遍历
const s = new Set([1,2,3,4]);
console.log(s.entries());{1 => 1, 2 => 2, 3 => 3, 4 => 4}

2:Map

类似对象,也是键值对,但是键的范围更大

const s = new Map([
    ['a',1],
    [100,2],
    [{},3],
    [[],4],
    [true,5],
    [undefined,6],
    [null,7],
    [Symbol(),8],
]);
 console.log(s); //{'a' => 1, 100 => 2, {…} => 3, Array(0) => 4, true => 5, …}

属性方法:

  • size:返回Map结构成员总数
  • set():设置键名对应的键值,返回Map结构,如果键名已有,键值会被更新,否则就生成新键
  • get():读取键名对应的键值,如果找不到,返回undefined
  • has():返回一个布尔值,表示某个键是否在当前Map中
  • delete:删除某个键,返回true
  • clear():清除所有成员
  • keys():返回键名
  • values():返回键值
  • entries():返回所有成员
  • forEach():遍历Map

十二:iterator

遍历器(Iterator)是一种机制。它是一种接口,为各种不同的数据结构提供统一的访问机制。任何数据结构只要部署 Iterator 接口,就可以完成遍历操作(即依次处理该数据结构的所有成员)

作用:一是为各种数据结构,提供一个统一的、简便的访问接口;二是使得数据结构的成员能够按某种次序排列;三是 ES6 创造了一种新的遍历命令for...of循环,Iterator 接口主要供for...of消费

  • 只要一种数据结构具有了Symbol.interator属性,那么就认为是可以迭代的
//为对象类型添加迭代器
let obj = {
     a: 1,
      b: 2,
}
Object.prototype[Symbol.iterator] = function () {
     let index = 0;
     let arr = Object.values(this);
     return {
         next() {
             return {
                  value: arr[index],
                  done: index++ >= arr.length
               }
           }
      }
}
for(let value of obj) {
     console.log(value);
} // 1,2
  • ES6中部署了iterator接口的有:Array,Set,Map,String