本文主要用于记录es6-11的学习过程,参考视频【尚硅谷Web前端ES6教程,涵盖ES6-ES11】

  1. ECMA:
    ECMA 欧洲计算机制造商协会
  2. ECMAScript:
    是ECMA国际通过ECMA-262标准化的脚本程序设计语言
  3. ECMA-262:
    它定制的一种标准
  4. 历史:
    每年都会更新一个版本 截至写稿已经是第十二版 即es12

let

和var类似 又有点不同

  • 声明变量

    1
    2
    3
    let a;
    let b = 521,g = 'dasda',h = [];
    //可以一次声明多个
  • 变量不能重复声明,但var可以。作用 防止变量被污染

  • 块级作用域 es5 全局 函数 eval

    1
    2
    3
    4
    5
    {
    let a = 'casc';
    }
    console.log(a);
    //这里会出错,但var可以,因为let只能在这个块级作用域里面生效
  • 不存在变量提升

    1
    2
    3
    4
    console.log(song);
    var song = 'aaa';
    //此时输出undefined 因为var声明的变量会提前赋一个undefined
    //但let不行
  • 不影响作用域链

  • 遍历绑定事件 假设数组长度为3

    1
    2
    3
    for(let i=0;i<items.length;i++){
    items[i].style.background = 'pink';
    }
  • 如果使用var修改 因为var没有块级作用域 它会一直执行下去,轮到里面的时候,i已经变成了3 而数组没有三的内容。

  • 而let由于有块级作用域,里面的内容独立存在,所以不会有全局影响

const

用于定义常量

  • 一定要赋初始值

  • 常量的值不能被修改

  • 块级作用域

  • 对于数组和元素的修改不算作对常量的修改 不会报错

    1
    2
    const team = ['scasc','casca'];
    team.push('ascasc');

解构赋值

es6允许用户按照一定模式从数组和对象中提取值

两种模式

  • 数组的解构

    1
    2
    const shuzu = ['aaa','cssca','casc'];
    let [a,b,c] = shuzu;
  • 对象的解构

    1
    2
    3
    4
    5
    6
    7
    8
    const obj = {
    name:'zzl',
    age:'20',
    function(){
    console.log("scasca");
    }
    }
    let {name,age,f} = obj;

模板字符串

引入新的声明字符方式 反引号`

  • 1
    let str = `dadadada`;
  • 内容中可以直接出现换行符

    1
    2
    3
    let str = `<ul>
    <li>aaaa</li>
    </ul>`
  • 变量拼接 ${}

    1
    2
    let a = '123';
    let b = `${a}被引用了`

简化对象

es6允许在大括号里面直接写入变量和函数作为对象的属性和方法

  • es6允许在大括号里面直接写入变量和函数作为对象的属性和方法

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    let name = 'zzl';
    let change = function(){
    console.log('asca');
    }

    const school = {
    //以前写法
    //name:name;
    //change:change;
    //improve:function(){
    //do sth.
    //}

    //现在写法
    name,
    change,
    improve(){
    cosole.log('new method');
    }
    }

箭头函数

允许使用箭头来定义函数=>

  • 允许使用箭头来定义函数

    1
    2
    3
    4
    5
    6
    7
    8
    //before 
    let fn = function(){
    //do sth.
    }
    //now
    let fn ()=>{
    //do sth.
    }

区别

  1. this指向的是静态资源

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    let getName1 = function(){
    console.log(this.name);
    }
    let getName2 = ()=>{
    console.log(this.name);
    }

    //设置window对象的name属性
    window.name = 'lalalla';
    const schoolName = {
    name: "babababab";
    }

    //直接调用 此时输出一致
    getName1();
    getName2();

    //call方法调用 此时 一输出babababab 二还是lalalal
    getName1.call(schoolName);
    getName2.call(schoolName);

  2. 不能作为构造实例化对象

    1
    2
    3
    4
    let Person = (name,age) =>{
    this.name = name;
    this.age = age;
    }
  3. 不能使用arguments变量

    1
    2
    3
    4
    let fn = () =>{
    console.log(arguments);
    }
    fn(1,2,3);
  4. 箭头函数的简写

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    //当形参只有一个的时候可以省略小括号
    let add = n =>{
    return n + n;
    }
    console.log(add(9));

    //省略花括号 当代码体只有一条语句的时候 此时return必须省略
    //而且语句的执行结果就是函数的返回值
    let pow = n => n * n;
    console.log(pow(2));

  • 需求1 点击div 2s之后变成粉色

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    case1 wrong
    <div id = "ad"></div>
    let ad = doucument.getElementById('ad');
    ad.addEventListener('click',function(){
    setTimeout(function(){
    this.style.background = 'pink';//此时由于定时器的this指向window 所以不会变色
    },2000);
    })

    case2 success
    <div id = "ad"></div>
    let ad = doucument.getElementById('ad');
    ad.addEventListener('click',function(){
    let that = this;//提前存储this
    setTimeout(function(){
    this.style.background = 'pink';
    },2000);
    })

    case3 success
    <div id = "ad"></div>
    let ad = doucument.getElementById('ad');
    ad.addEventListener('click',function(){
    setTimeout(()=>{
    this.style.background = 'pink';
    //使用箭头函数 会找到外面一级的对象
    },2000);
    })
  • 需求二 从数组中返回偶数元素

    1
    2
    const arr = [1,2,33,4342,4];
    const result = arr.filter(item => item%2 ===0 );

总结

  • 箭头函数适合与this无关的回调,定时器,数组的方式回调

  • 不适合与this有关的回调,比如事件回调,对象的方法

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    {
    name:'abc';
    getName:function(){
    console.log(this.name);//可以返回abc
    }
    }
    {
    name:'abc';
    getName:()=>{
    console.log(this.name);//不可以返回abc,因为此时this指向了window
    }
    }

参数默认值

ES6允许给函数形参赋初始值

  • 形参初始值具有默认值的参数 一般位置要靠后 (潜规则)

    1
    2
    3
    4
    5
    6
    function add(a,b,c=10){
    return a+b+c;
    }
    console.log(add(1,2));//此时如果不给c传值 那么c默认是10

    结果:13
  • 与解构赋值结合

    1
    2
    3
    4
    5
    6
    7
    8
    connect({
    host:'localhost',
    port:3000
    })
    function connect({host='127.0.0.1",port}){
    console.log(host);
    console.log(port);
    }

rest参数

ES6引入rest参数,用于获取函数的实参,用来代替arguments

获取实参的方式

  • arguments 此时获取的是一个对象

    1
    2
    3
    4
    function getShican(){
    console.log(arguments);
    }
    getShican('leb','zzl');
  • rest 参数 三个点加args 此时获取的args是数组 意味着可以用数组的方法

    1
    2
    3
    4
    function getS(...args){
    console.log(args);
    }
    getS('leb','zzl');
  • rest参数必须放到最后

    1
    2
    3
    4
    5
    6
    7
    function getS(a,b,...args){
    console.log(args);
    }
    getS('leb','zzl',1,2,3,4);
    a=leb
    b=zzl
    args=[1,2,3,4]

spread拓展运算符

… 拓展运算符可以将数组转换为逗号分隔的参数序列

例子

  • 声明一个函数

    1
    2
    3
    4
    5
    6
    7
    8
    const jojo = ['jotailang','jolunuo','jolin'];
    function getS(){
    console.log(arguments);
    }
    gets(...jojo);

    此时arguments里面有三个参数:'jotailang','jolunuo','jolin'
    否则就是一个参数

和rest区别

  • rest的声明放在函数声明的形参中,这个是放在函数调用的形参中

拓展运算符的运用

  • 数组的合并

    1
    2
    3
    4
    5
    6
    const jojo = ['jolin','jostar'];
    const kingdomrank = ['boji','kake'];
    //const theworld = jojo.contat(kingdomrank);
    //or
    //注意使用逗号分割
    const theworld = [...jojo,...kingdomrank];
  • 数组的克隆

    1
    2
    const jojo = ['saigouda'];
    const clonejojo = [...jojo];
  • 将伪数组转化为真正的数组

    1
    2
    3
    4
    5
    6
    <div></div>
    <div></div>
    <div></div>

    const divs = document.querySelectorAll('div');
    const divarr = [...divs];

Symbol基本使用

ES6引入一种新的原始数据类型Symbol,表示独一无二的值,它是js语言中的第七种数据类型,是一种类似字符串的数据类型。

特点

  • 它的值是唯一的,用来解决命名冲突的问题
  • 不能和其他数据进行运算
  • 它定义的对象属性不能使用for…in进行遍历,但是可以使用Reflect.ownkeys来获取对象的所有键名

创建

  • 创建Symbol

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    let s = Symbol();

    let s2 = Symbol('jojo');
    let s3 = Symbol('jojo');
    console.log(s2 === s3);
    //false

    //another way
    let s4 = Symbol.for('jojo');
    let s5 = Symbol.for('jojo');
    console.log(s4===s5);
    //true
  • 不能与其他数据进行运算

  • 向对象中添加方法up down

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    let game = {...}

    let methods = {
    up:Symbol(),
    down:Symbol()
    };

    game[methods.up] = function(){
    console.log('i can up');
    }
    game[methods.down] = function(){
    console.log('i can down');
    }
  • 当想往对象中添加方法的时候,一般要了解对象中的参数,而且存在风险,用这种方式声明的方法,没有风险,可以不用看对象的内容就可以添加

  • 方法2

    1
    2
    3
    4
    5
    6
    7
    let youxi = {
    name:'狼人杀',
    [Symbol('say')]: function(){
    console.log('i can speak');
    }
    }
    console.log(youxi)
  • Symbol内置值

JS的七种数据类型

USONB u are so niubility
  • u undefined
  • s string symbol
  • o object
  • n null number
  • b boolean

迭代器

迭代器(Iterator)是一种接口,为各种不同的数据结构提供统一的访问机制。任何数据结构只要部署Iterator接口,就可以完成遍历操作。

  • es6创造了一种新的遍历命令for…of循环,Iterator接口主要供其消费

  • 原生具备iterator接口的数据(可以用for..of遍历)

    1
    2
    3
    4
    5
    6
    7
    a Array
    b Arguments
    c Set
    d Map
    e String
    f TypedArray
    g NodeList

工作原理

  • 首先创建一个指针对象,指向当前数据结构的起始位置

  • 第一次调用对象的next方法,指针自动指向数据结构的第一个成员

  • 接着不断调用next方法,指针一直往后移动,直到指到最后一个成员

  • 每调用next方法返回一个包含==value和done==属性的对象

    1
    2
    value:当前成员的值
    done:布尔值 表示遍历是否结束 若未结束 返回false

注意

  • 需要自定义遍历数据的时候,要想到迭代器

生成器

  1. 生成器是一个特殊的函数
  2. 生成器目的是解决异步编程中的回调问题
  3. 回调函数 node fs ajax mongodb
  • 写法上特殊

    1
    2
    3
    4
    function * gen(){
    console.log('hello generator');
    }

  • 输出上特殊

    1
    2
    let iterator = gen();
    iterator.next();
  • yield分割符

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    function * gen(){
    console.log('111');
    yield '分割1';
    console.log('222');
    yield '分割2';
    console.log('333');
    yield '分割3';
    }
    let iterator = gen();
    iterator.next();
    iterator.next();
    iterator.next();
  • 输出yield的值 遍历

    1
    2
    3
    for(let v of gen()){
    console.log(v);
    }
  • 迭代器方法

    1
    2
    3
    4
    let iterator = gen();
    console.log(iterator.next());
    console.log(iterator.next());
    console.log(iterator.next());

生成器函数传参

  • 整体传参

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    function * gen(args){
    console.log(args);
    yield 111;
    }
    let iterator = gen('aaa');
    console.log(iterator.next());

    logout:
    aaa
    value:111 done:false
  • 方法传参

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    function * gen(args){
    console.log(args);
    let one = yield 111;
    console.log(one);
    yield 222;
    }
    let iterator = gen('aaa');
    console.log(iterator.next());
    console.log(iterator.next('bbb'));

    logout:
    aaa (args)
    value 111 done false
    bbb (one)
    value 222 done false

    注意 此时的bbb是第一个yield的整体结果

对于异步编程的作用案例

  • 假如需要1s 输出aaa 2s输出bbb 3s输出ccc

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    常规操作 setTimeout嵌套
    现在利用生成器
    function one(){
    setTimeout(()=>{
    console.log('aaa');
    iterator.next();
    },1000)
    }
    function two(){
    setTimeout(()=>{
    console.log('bbb');
    iterator.next();
    },2000)
    }
    function three(){
    setTimeout(()=>{
    console.log('ccc');
    iterator.next();
    },3000)
    }
    function * gen(){
    yield one();
    yield two();
    yield three();
    }
    let iterator = gen();
    iterator.next();

Promise

Promise是es6引入的异步编程的新解决方法,语法上他是一个构造函数,主要用来封装异步操作获取他失败或者成功的结果。(为了解决回调地狱的问题)

实例化Promise对象

1
2
3
4
5
6
7
8
9
10
11
12
13
14
const p = new Promise(function(resolve,reject){
//使用异步操作
setTimeout(function(){
let data = 'jojo';
//调用resolve/reject来改变这个promise对象的状态
resolve(data);
},1000);
})
//调用promise对象的then方法
p.then(function(value){
console.log(value);
},function(reason){
console.error(reason)
})
  • promise对象有三种状态
  1. pending 进行中
  2. fulfilled 已成功
  3. rejected 已失败
  • then有两个形参,成功一般叫value 失败叫reason
  • 只要执行了resolve 就会调用then函数里面的value方法,反之调用reason方法

  • 调用then方法,then方法返回的结果是一个promise对象,对象有对象状态和对象值这两个参数,对象的状态由方法的的执行结果而定

  1. 如果回调函数中返回的结果是一个非promise类型的属性 则状态为成功,返回改属性值

    1
    2
    3
    4
    5
    6
    7
    const result =  p.then(function(value){
    console.log(value);
    return 'jojo';
    })
    logout:
    promise.status:'resolve';
    promise.value:'jojo';
  • 此外如果不写return 那么返回的是undefined 也是非promise类型的属性 所以也会成功 并且返回 undefind
  1. 如果回调函数中返回的结果是一个promise类型的属性,则该属性的状态决定then方法的状态

    1
    2
    3
    4
    5
    6
    const result =  p.then(function(value){
    console.log(value);
    return new Promise(function(resolve,reject){
    resolve('jojo');
    })
    })
  2. 抛出错误 那么失败值就是抛出的值

    1
    2
    3
    4
    const result =  p.then(function(value){
    console.log(value);
    throw new Error('出错了');
    })
  • 链式调用

    1
    2
    3
    4
    5
    p.then(value=>{

    }).then(value=>{

    });
  • promise-catch方法 作用原理和不写第一个value的then方法相同

    1
    2
    3
    4
    //用于写错误情况
    p.catch((reason)=>{
    console.warn(reason);
    })
  • promise读取文件 注意err和data不要写反

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    const fs = require('fs');

    const p = new Promise(function(resolve,reject){
    fs.readFile('./lalala.md',(err,data)=>{
    if(err) reject(err);
    resolve(data);
    })
    })
    p.then(function(value){
    console.log(value.toString());
    },function(reason){
    console.error(reason);
    })
  • promise封装ajax 在promise之前,所有成功或者失败的操作都要在事件里面操作,不方便阅读,现在使用promise封装,函数成功和失败的操作都在p.then()里面完成

  • promise读取多个文件 下面以三个文件为例子

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    const fs = require('fs');

    const p = new Promise((resolve, reject)=> {
    fs.readFile('./a.md', (err, data) => {
    resolve(data);
    })
    })
    p.then((value) => {
    return new Promise((resolve, reject) => {
    fs.readFile('./b.md', (err, data) => {
    resolve([value,data]);//将结果转化为数组的形式发送到下一个,因为这个数组的结果就是当前then方法的值
    })
    })
    }).then((value) => {
    return new Promise((resolve, reject) => {
    fs.readFile('./c.md', (err, data) => {
    value.push(data);//因为上一个传入的是数组 所以现在要读取这个数据需要将其压入数组
    resolve(value);
    })
    })
    }).then((value) => {
    console.log(value.join('\r\n'));
    });

Set

ES6提供了新的数据结构set集合,类似于数组,但成员的值都是唯一的,集合实现了iterator接口,所以可以使用拓展运算符…和for..of进行遍历。

  1. 基本定义

    1
    2
    let s = new Set();
    console.log(s, typeof s);
  2. 可以实现自动去重 但注意这里还不是数组

    1
    2
    let s2 = new Set(['aaa','bbb','aaa','ccc']);
    log out: aaa,bbb,ccc
  3. size 返回集合的元素个数

    1
    s2.size;
  4. add 增加一共新元素 返回当前集合

    1
    s2.add('ddd');
  5. delete 删除当前元素 返回boolean值

    1
    s2.delete('aaa');
  6. has 检测集合中是否包含某个元素,返回boolean值

    1
    s2.has('bbb');
  7. clear 清空元素

    1
    s2.clear();
  1. 数组去重 上面说到去重的办法,但是他还是集合的形式,要通过拓展运算符把他变成数组

    1
    2
    3
    let arr = [1,2,3,4,5,4,3,2,1];
    let result = [...new Set(arr)];
    console.log(result);
  2. 交集 注意先去重

    1
    2
    3
    4
    5
    6
    let arr = [1,2,3,4,5,4,3,2,1];
    let arr2 = [1,2,3];
    let s2 = new Set(arr2);
    //去重之后和arr2进行比对
    let result = [...new Set(arr)].filter(item=> new Set(arr2).has(item));
    console.log(result);
  3. 并集 注意数组拼接之前需要转化,以及最后去重之后要转化为数组

    1
    let result = [...new Set([...arr,...arr2])];
  1. 差集 就是交集的取反

    1
    2
    3
    4
    5
    6
    let arr = [1,2,3,4,5,4,3,2,1];
    let arr2 = [1,2,3];
    let s2 = new Set(arr2);
    //去重之后和arr2进行比对
    let result = [...new Set(arr)].filter(item=> !(new Set(arr2).has(item));
    console.log(result);

Map

ES6提供了Map数据结构,它类似于对象,也是键值对的集合,但是键的范围不仅限于字符串,各种类型的值,包括对象 都可以作为键。Map也实现了iterator接口,可以使用拓展运算符…和for..of遍历

基本方法

  1. size 返回map的元素个数
    1
    2
    const m = new Map();
    m.size();
  2. set 增加一个新的元素

    1
    m.set('jojo','saigouda');
  3. get 返回键名对象的键值

    1
    m.get('jojo');
  4. has 检测其中是否含有某个元素,返回boolean值

    1
    console.log(m.has('jojo'))
  5. clear 清空map
    1
    m.clear();
  6. 遍历
    1
    2
    3
    for(let v of m){
    console.log(v);
    }

Class

ES6提供了更接近传统的写法,引入了class类这个概念,作为对象的模板。通过class关键字,可以定义类,基本上,es6的class可以看作是一个语法糖,它的绝大部分功能es5都可以做到,新的class写法只是让对象原型的写法更加清晰,更像面向对象编程的语法

之前es5的方法

1
2
3
4
5
6
7
8
9
10
11
12
function Phone(brand,price){
this.brand = brand;
this.price = price;
}

//添加方法
Phone.prototype.call = function(){
console.log('i can call');
}
let huawei = new Phone('huawei','2999');
huawei.call();
console.log(huawei)

现在的方法
1
2
3
4
5
6
7
8
9
10
11
12
class JOJO{
constructor(name,stand){
this.name = name;
this.stand = stand;
}
//方法必须使用该语法 不能使用es5的call:function(){}
call(){
console.log('oraoraoraoraora!!!');
}
}
let jotaro = new JOJO("jotaro","starplj");
console.log(jotaro);

  1. 类的静态成员
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    class Phone{
    static name = 'lalala';
    static change(){
    console.log('cascacs')
    };
    }
    let nokia = new Phone();
    console.log(nokia.name);
    //此时会输出undefine 因为name是类的静态属性,不是实例对象的属性
    console.log(Phone.name);
    //logout:lalala
  2. 类的继承
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    //先写一个父类
    function Phone(brand,price){
    this.brand = brand;
    this.price = price;
    }
    Phone.prototype.call = function(){
    console.log('我可以打电话');
    }
    //子类
    function SmartPhone(brand,price,color,size){
    Phone.call(this,brand,price);
    this.color = color;
    this.size = size;
    }
    SmartPhone.prototype = new Phone;
    SmartPhone.prototype.constructor = SmartPhone;

    SmartPhone.prototype.photo = function(){
    console.log('我可以拍照');
    }
    SmartPhone.prototype.playGame = function(){
    console.log('我可以玩游戏');
    }

    const chuizi = new SmartPhone('锤子',2499,'黑色','5.5inch');

    console.log(chuizi);
  3. 类的继承2
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    class Phone{
    constructor(brand,price){
    this.brand = brand;
    this.price = price;
    }
    call(){
    console.log('我可以打电话');
    }
    }
    class SmartPhone extends Phone{
    constructor(brand,price,color,size){
    super(brand,price);//Phone.call(this,brand,price)
    this color = color;
    this size = size;
    }
    photo(){
    console.log('拍照');
    }
    playGame(){
    console.log('玩游戏');
    }
    }
    const xiaomi = new SmartPhone('小米',799,'黑色','4.22inch');
    console.log(xioami);
    xiaomi.call();
    xiaomi.photo();
    xiaomi.playGame();

  4. 子类重写父类方法 重写方法 这个方法可以重写但不能调用父类的
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    class Phone{
    constructor(brand,price){
    this.brand = brand;
    this.price = price;
    }
    call(){
    console.log('我可以打电话');
    }
    }
    class SmartPhone extends Phone{
    constructor(brand,price,color,size){
    super(brand,price);//Phone.call(this,brand,price)
    this color = color;
    this size = size;
    }
    call(){

    }
    }
    const xiaomi = new SmartPhone('小米',799,'黑色','4.22inch');
    xiaomi.call();
  5. get与set
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     class Phone{
    get price(){
    console.log('价格属性被读取了');
    return 'i love u';
    }
    set price(newVal){
    console.log('价格属性被修改了');
    }
    }
    let s = new Phone();
    //console.log(s.price);
    s.price = 'free';

数值拓展

ES6定义了几种数值拓展,对于数值检测很有帮助

  1. Number.EPSILON 是js表示的最小精度,约等于2.2x10的-16次方
    1
    2
    3
    4
    function equal(a,b){
    return Math.abs(a-b)<Number.EPSILON;
    }
    console.log(equal(0.1+0.2,0.3));
  2. 进制数
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    // 二进制
    let b = 0b1010;
    // 八进制
    let o = 0o777;
    // 十进制
    let d = 10;
    // 十六进制
    let x = 0xff;
    console.log(b);
    console.log(o);
    console.log(d);
    console.log(x);
  3. Number.isFinite 检测一个数是否为有限数
    1
    2
    console.log(Number.isFinite(Infinity));
    //返回false
  4. Number.isNaN 检测一个数值是否为NaN
  5. Number.parseInt Number.parseFloat 字符串转整数
  6. Number.isInteger() 判断整数
  7. Number.trunc 将小数部分抹掉
  8. Math.sign 判断是否为正数 负数 0 如果是正数为1 负数为-1 0为0

对象方法拓展

  1. Object.is 判断两个值是否完全相等 可以判断NaN这种特殊类型
    1
    2
    3
    4
    console.log(Object.is(NaN,NaN));
    //true
    console.log(NaN === NaN);
    //false
  2. Object.assign 对象的合并 会覆盖原先对象有的属性 没有的属性不会覆盖
  3. Object.setPrototypeOf Object.getPrototypeOf
    1
    2
    3
    4
    5
    6
    7
    8
    9
    const school = {
    name:'广师大'
    }
    const cities = {
    xiaoqu:['gz','hy']
    }
    Object.setPrototypeOf(school,cities);
    console.log(Object.getPrototypeOf(school));
    console.log(school);

ES6模块化

模块化是指将一个大的文件,拆分成许多小的文件,然后将小的文件组合起来
优点:

  1. 防止命名冲突
  2. 代码复用
  3. 高维护性

模块功能主要由两个命令组成:export和import

  • export用于规定模块的对外接口
  • import命令用于输入其他模块提供的功能

    需要在vscode里面安装liveserver插件

  1. export 分别暴露
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    //新建一个new.js
    export let jojo = 'jojo';

    export function change(){
    console.log('balalalalnananan1');
    }
    //再新建一个index.html
    <!DOCTYPE html>
    <html lang="en">
    <head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    </head>
    <body>
    <script type="module">
    import * as m1 from "./new.js";
    console.log(m1);
    </script>
    </body>
    </html>
  2. export 统一暴露

    1
    2
    3
    4
    5
    6
    7
    let jojo = 'jojo';

    function change(){
    console.log('balalalalnananan1');
    }

    export {jojo,change};
  3. export 默认暴露

1
2
3
4
5
6
7
export default{
let jojo = 'jojo';

function change(){
console.log('balalalalnananan1');
}
}

解构赋值

  1. 应对统一暴露 当已经有声明的对象的时候 可以采用取别名的方法
    1
    2
    import {jojo,change} from './newjs';
    import {jojo as newjojo,change} from './newnewjs';
  2. 应对默认暴露 写法必须起别名
    1
    import {default as m3} from './newjs'

简便形式 只能应对默认暴露

1
import m3 from './newjs'

以上的方法如果在多个模块的时候很不方便 可以使用下面的方法

1
2
3
4
//新建一个app.js
import * as m1 from './m1.js';
//在html中引入
<script src='./app.js' type="module"></script>

Babel

一款代码兼容性转化软件/网站。可以将新特性的代码转化为兼容性的代码

需要安装三个工具

  1. babel-cli babel的一个命令行工具
  2. babel-preset-env 预设包 可以将最新的es特性转化为es5的语法
  3. browserify 一个打包工具 (比较简单)

流程

  1. 初始化npm init --yes
  2. npm i babel-cli babel-preset-env browserify -D
  3. 局部安装使用npx 全局安装使用babel
  4. npx babel js路径 -d 转移到新js路径 --presets=babel-preset-env
  5. 打包npx browserify dist/js/app.js -o dist/bundle.js(前者入口js,后者保存路径)
  6. 总结 先编译 再打包

引入NPM包

ES7新特性