ES6新增

  • ES全称EcmaScript 是脚本语言的规范 而平时经常编写的JavaScript,是EcmaScript的一种实现 所以ES新特性其实值得就是JavaScript的新特性
  • 为什么学习新特性?
    • 1 语法简写 功能丰富
    • 2 框架开发应用
    • 3 前端开发职位要求
  • ECMAScript 相关介绍
    • 什么是ECMA
      • ECMA(European Computer Manufacturers Association) 中文名称为欧洲计算机制造协会,这个组织的目标是评估、开发和认可电信和计算机标准 1994年后该组织改名为Ecma国际
  • ES6中的7种数据类型
    • USONB
      • u undefined
      • s string symbol
      • o object
      • n null number
      • b boolean
  • let 关键字
    • let和var声明变量的方式一样
    • let声明变量的特性
      • let变量不能重复声明
      • let声明的变量具有块级作用域 也就是局部作用域
      • let不具有变量提升
      • 不影响作用域链
  • const关键字
    • 1 const 声明常量并赋值
    • 2 一般常量大写 小写也可以 潜规则大写
    • 3 常量不能被修改
    • 4 有块级作用域
    • 5 对于数组和对象的元素修改 不算做对常量的修改 不会报错

      ES6新增_第1张图片

  • 变量解构赋值
    • const arr = ["a","b","c"] 声明一个常量
      • let["aa","bb","cc"] = arr; 定义的变量中的值和常量中的值一一对应
  • 对象的结构赋值
    • 将对象拆封再分开赋值

      ES6新增_第2张图片

  • 简化对象写法
    • ES6 允许在发括号中直接写入变量和函数 作为对象的属性和方法
    • 这样的书写更简洁
    • 如果在外部声明一个变量并赋值 则可以在打括号中直接使用变量掉调用

      ES6新增_第3张图片

  • ES6中的箭头函数
    • let fn = (a,b)=>{ return a+b } 创建一个箭头函数
    • let 变量 = fn(1,2); console.log(变量) 调用函数
    • 箭头函数和普通函数的区别
      • 1 this是静态的 this始终执行函数声明是所在作用域下的this的值 使用bind等方法不能改变箭头函数中this的指向

        ES6新增_第4张图片

      • 2 不能作为构造函数实例化对象
      • 3 不能使用 arguments 变量
        • arguments 是一个特殊的变量 用于保存实参
        • let fun = () =>{console.log(arguments)} 创建一个使用arguments储存变量的函数、
        • fun(1,2,3) 调用函数 返回值报错 arguments 变量没有定义
      • 箭头函数适合与this无关的问题 定时器 数组的方法回调
      • 箭头函数不适合于this有关的回调 事件回调 对象的方法
      • 箭头函数的简写
        • 1)省略小括号 当形参有且只有一个的时候
          • let add = n =>{return n + n} 创建一个箭头函数
          • console.log(add(9)) 调用箭头函数
        • 2)省略花括号 当代码只有一条语句时候可以省略 此时return也必须省略 此时语句的执行结果就是函数的返回值
          • let pow = (n) => n*n; 创建函数
          • console.log(pow(9)) 调用函数
          • 小案例点击div 2秒后颜色变成粉色
            • 高级js经典案例 保存this的值

              ES6新增_第5张图片

            • 使用箭头函数 更简洁

              ES6新增_第6张图片

  • ES6中的参数默认值
    • ES6允许给函数参数赋值初始值
    • 1. 形参初始值
      • function add(a,b,c=10){return a + b + c} //在形参中赋值的参数放到最后面
        • let result = add(1,2)
    • 2. 与解构赋值结合
      • 如果给host赋值就是用赋值的 如果不赋值 就是用在函数中给形参赋值的默认值

        ES6新增_第7张图片

  • ES6中rest参数 用于获取函数的实参 用于代替 arguments
    • rest参数必须要放到参数的最后 就是(...a)接收所有的参数 如果不放到最后会报错
    • es5中获取实参的方式是、
      • function date(){console.log(arguments)} 创建函数
      • date("白芷","阿娇","杨过") 返回值是一个对象的形式
    • ES6中的rest参数
      • function date(...args){console.log(args)} 创建函数
      • date("白芷","阿娇","杨过") 返回值是一个数组
  • ES6 扩展运算符 [...] 能将数组转换为逗号分隔的参数序列
    • 使用...加上一个数组就可以将数组转换为一个参数序列用逗号分隔
    • 声明一个数组
      • const tfboys = ['a','b','c']
      • 声明一个函数
        • function chunwan(){console(arguments)}
        • chunwan(...tfboys) //等同于chunwan('a','b','c')
    • 扩展运算符的使用
      • 1. 数组的合并
        • const arr1 = ['a','b'] 创建数组1
        • const arr2 = ['c','d'] 创建数组2
        • const arrs = [...arr1,...arr2] 就可以将两个数组合并成一个新数组 中间需要使用逗号隔开

          ES6新增_第8张图片

      • 2. 数组的克隆
        • const arr1 = ['a','b'] 创建数组
        • const arr2 = [...arr1]; //如果数组中有数据的引用是一个浅拷贝形式 如果没有则是完全形式的复制

          ES6新增_第9张图片

      • 3. 将伪数组转换成真正的数组
        • const arr = [...伪数组] //arguments也可以将伪数组转换成真正的数组
  • ES6 Symbol 的基本使用
    • ES6引入了一种新的原始数据类型 Symbol 表示独一无二的值 它是javaScript 语言的第七种数据类型 是一种类似于字符串的数据类型
    • Symbol 的特点
      • 1)Symbol 的值是唯一的 用来解决命名冲突的问题
      • 2)Symbol 值不能与其他数据进行运算
        • s + 100 或 s >100 返回值都是报错
      • Symbol 定义的对象属性不能使用 for..in 循环遍历 但是可以使用Reflect.ownKeys 来获取对象的所有键名
    • Symbol 的两大类创建
      • let s = Symbol() 创建Symbol
        • console.log(s, typeof s); //返回值为 Symbol() "symbol" 唯一性面板中不可见 内部已经完成了唯一性
        • let s1 = Symbol(1) 创建两个对象
        • let s2 = Symbol(1)
        • log(s1 === s2); //返回值为false 因为数组存储地址不同所以两个对象并不相等
      • 使用Symbl.for 创建 创建出来的被称之为函数对象
        • let s4 = Symbol.for('ss'); console.log(s4,type s4) 返回值为 s4为Symbl(ss) type s4返回值为"Symbl"类型
        • let s5 = Symbol.for('ss');
        • log(s4 === s5 ); 返回值为 true 因为两个值所调用的存储地址相同
    • Symbol 的使用 一般给对象添加属性或方法
      • let youxi = {name:'a' [Symbol('say')]:function(){console.log("啊啊啊")}}

        ES6新增_第10张图片

      • 想调用可以这样:首先,在函数体内部,把[Symbol('say')]改成[Symbol.for('say')]
      • 其次,在对象youxi外定义变量let say = Symbol.for('say')
      • 最后,在对象youxi外部调用:youxi[say]()。
    • Symbol 的内置值
      • 内置值就是除了定义自己使用的Symbol 值以外的方法 这个属性用来做对象的属性 指向属性的方法
      • Symbol.hasInstance 当其他对象使用 instanceof 运算符判断是否为该对象的实例时调用这个方法

        ES6新增_第11张图片

      • Symbol.isConcatSpreadable 对象的属性等于一个布尔值 表示该对象用于Array.prototype.concat()时 是否可以展开 例( arr2[symbol.isConcatSpreadable] = false)
        • const arr1 = [1,2,3]
        • const arr2 = [4,5,6]
        • arr1.concat(arr2) //就返回一个新数组[1,2,3,4,5,6]
        • 如果使用 arr2[symbol.isConcatSpreadable] = false 当后面的值为false的时候
          • arr1.concat(arr2) 使用合并数组 则返回值为[1,2,3,Array(3)] 以一个数组的整体形势合并
      • Symbol.unscopables 该对象使用 with 关键字时 哪些属性会被 with环境排除
      • Symbol.match 当执行 str.match(myObject) 时 如果该属性存在 会调用它 返回该方法的返回值
      • Symbol.replace 当对象被str.replace(myObject) 方法调用时 会返回该方法的返回值
      • Symbol.search 当该对象被 str.search(myObject) 方法调用时 会返回该方法的返回值
      • Symbol.split 当该对象被str.split(myObjcet)方法调用时 会返回该方法的返回值
      • Symbol.iterator 对象进行for....of 循环时 会调用Symbol.iterator 方法 返回该对象的默认遍历器 迭代器
      • Symbol.toPrimitive 该对象被转为原始类型的值时 会调用这个方法 返回该对象对应的原始类型值
      • Symbol.toStringTag 该对象上面调用 toString 方法是 返回该方法的返回值
      • Symbol.species 创建衍生对象是 会使用该属性
      • 总结 可以将Symbol 当做一个永远都不会重复的字符串就行了
  • 迭代器
    • 需要遍历自定义数据的时候 可以使用迭代器
    • 迭代器(Iterator) 是一种接口 为各种不同的数据结构提供统一的访问机制 任何数据结构只要不熟 Iterator接口 就可以完成遍历操作
    • 1)ES6 创造了一种新的遍历命令 for...of循环 Iterator 接口主要供 for...of 使用
      • for ...in 返回的是索引 for...of 返回的是索引对应的值
    • 2)原生具备Iterator接口的数据 都可用 for...of遍历 以下对象类型都具有Iterator接口
      • a) Array
      • b) Arguments
      • c) Set
      • d) Map
      • e) String
      • f) TypedArray
      • g) NodeList
    • 3)工作原理
      • a) 创建一个指针对象 指向当前数据结构的其实位置
      • b) 第一次调用对象的 next方法 指针自动指向数据结构的第一个成员
      • c)接下来不断调用 next 方法 指针一直往后移动 直到指向最后一个成员
      • d) 每调用next方法 返回一个新的包含value 和done属性的对象

        ES6新增_第12张图片

        • dong 在此表示一个完成值 若为true则就表示已经将对象所有值返回完成
    • 迭代器自定义遍历对象
      • 在对象中自己添加迭代器接口/方法

        ES6新增_第13张图片

  • 生成器
    • 生成器函数是ES6 提供的一种异步编程解决方案 语法行为与传统函数完全不同
    • 生成器其实就是一个特殊的函数
    • 生成器的作用就是进行异步编程 以前进行异步编程都是使用回调函数
    • function * fun(){console.log("aaa") yield '111'; console.log("bbb") yield '222')} 生成器的函数创建 需要在函数名前加一个*号
      • yield 可以认为值代码的分隔符
    • let iterator = fun() iterator.next(); 需要使用变量名加next() 才可以调用 每一次调用 next返回 分隔符到前一个分隔符或后一个分隔符中间的内容 调用一次返回一段

      ES6新增_第14张图片

    • 生成器函数的参数
      • 生成器一定是迭代器 迭代器不一定是生成器
      • 异步编程 文件操作 网络操作 (ajax,request) 数据库操作
      • next() 调用的时候可以在括号中穿入实参 第二次调用next()方法时 会将在括号中传如的实参当做第一个yield整体返回的结果 就像整体调用回调函数

    • 生成器函数实例 与红绿灯效果类似

      ES6新增_第15张图片

    • 生成器案例2 异步操作同步执行

      ES6新增_第16张图片

  • Promise
    • Promise 是 ES6 引入的异步编程的新解决方案 语法上Promise 是一个构造函数 通过他可以实例化对象 用来封装异步操作并可以获取其成功或失败的结果
    • 1)Promise 构造函数:Promise(excutor){}
    • 2) Promise.prototype.then 方法
    • 3)promise.prototype.cath 方法
    • 实例化promise对象
      • 对象有三种状态 分别是 初始化 成功(resolve) 失败(reject)
      • const p = new Promise(function(resolve,reject){在这里定义异步操作})
        • 当数据成功的时候
          • 当调用resolve的时候 对象的状态就会变成成功
          • 如果返回成功 就可以调用promise 对象中的 then方法
            • 一般将成功的形参叫做value 失败的形参叫做reason
          • 调用resolve之后 then方法就会执行then方法中的第一段回调函数代码
        • 当数据读取失败的时候 会调用then方法中的第二个回调函数

          ES6新增_第17张图片

      • promise 读取文件内容 读取文件夹中的文件
        • 调用方法读取文件

          ES6新增_第18张图片

        • 使用promise 封装读取文件的方法 将整个方法封装成一个实例化对象 在外面调用then方法

          ES6新增_第19张图片

          • 使用promise 方法有一个界限 让代码不会一直向下缩进 避免回调地狱
            • 因为多个任务就要嵌套了,一层层往里面嵌套,那又为什么要嵌套?因为不嵌套的话代码的运行时间又会大大增加,为什么代码运行时间会增加?因为js是单线程的。在同一时间内只有一个主线程会执行,异步的线程暂停
            • 不是异步的线程,因为不是嵌套,就是排队执行的同步任务,这样只能等前面一个任务完全执行完才能执行后面的任务。嵌套的程序就是异步任务,不会被前面的任务堵塞,可以顺畅的执行。
      • promise封装方法就是 先将方法实例化成一个promise参数 然后将其中的判断条件if...eles中执行的结果加上resolve(成功) reject(失败) 就比如在 if判断条件为成功的时候 在if的执行语句前 加上resolve方法 比如成功要conleon.log(1) 要打印1这个数字 就写成 resolve(1) 然后在外面使用实例化的常量去掉用then方法去执行 可以将resolve(1) 当做 conleon.log(1) 只不过在外面使用then方法可以进行下一步操作 使用promise因为管理性强 后续操作可以在外面进行 不会影响封装好的代码

        ES6新增_第20张图片

    • promise 中的then方法
      • then方法可以指定两个回调函数 then方法的返回结果是promise对象 对象状态由回调函数的执行结果决定的
        • then(函数1,函数2) 如果promise方法成功的话 就调用第一个回调函数 如果失败就调用第二个回调函数
        • 1.如果回调函数 中返回的结果是非 promise类型的属性 状态为成功 返回值为对象成功的值
        • then返回的状态以promise的返回值为准 如果promise返回失败 then返回的结果也是失败
        • Promise有三种状态,如果用Promise()构造器创建一个Promise对象,当被创建时,它的状态是pending,如果一个Promise对象的resolve方法被调用,它的状态会变成fulfilled,而如果一个Promise对象的reject方法被调用,它的状态会变成rejected。此外,还有两种初始化Promise对象的方法,分别是Promise.resolve方法和Promise.reject方法,前者会直接返回一个状态为fulfilled的Promise对象而后者会直接返回一个状态为rejected的Promise对象。
        • 在一个Promise链中,如果一个Promise状态变成了fulfilled,它会自动在Promise链中向下寻找,直到发现一个then方法,并执行其中的第一个参数函数,而如果一个Promise的状态变成了rejected,它会在Promise链中向下寻找,直到发现一个带有两个参数的then方法并执行它的第二个参数函数或发现一个catch方法并执行它的参数函数。
      • promise 小案例 读取多个文件
        • 回调地狱问题之一 函数形参重名 不易被发现
        • 回调地狱写法

          ES6新增_第21张图片

        • 使用 promise 读取

          ES6新增_第22张图片

    • promise 中的 catch方法 该方法指定一个失败的回调函数 使用then中的失败回调也一样
  • Set
    • ES6提供了新的数据结构 Set集合 它类似于数组 但成员的值都是唯一的 集合实现了 iterator接口 所以可以使用 扩展运算符 和 for...of... 进行遍历 集合的属性和方法
      • 1)size 返回集合的元素个数、
      • 2)add 增加一个新元素 返回当前集合
      • 3)delete 删除元素 返回boolean值
      • 4)has 检测集合中是否包含某个元素 返回 boolean值
      • 5)clear() 清空集合中的所有数据
    • Set集合会去除集合中的重复的值

      ES6新增_第23张图片

    • 使用Set实现两个数组的交集 就是获取两个数组中都有的值
      • let result = [...new Set(arr)].filter(item=>new Set(arr2).has(item)); //arr 和 arr2就是两个数组
    • 将两个集合 合并 并去重 let newarr = [...new Set([...arr, ...arr2])];
    • 将两个集合中互相没有的数据保留 let diff = [...new Set(arr)].filter(item=> !(new Set(arr2).has(item)));
  • Map
    • ES6 提供了Map 数据结构 它类似与对象 也是键值对的集合 但是 键 的范围不限于字符串 各种类型的值 包括对象就可以当做键 Map也是实现了 iterator 接口 所以可以使用 扩展运算符 和 for...of... 进行遍历 Map 的属性和方法:
    • 1)size 返回Map的元素个数
    • 2)set 增加一个新元素 返回当前Map
    • 3)get 返回键名对象的键值
    • 4)has 检测Map中是否包含某个元素 返回boolean值
    • 5)clear 清除集合 返回undefined
    • Map方法使用
      • 声明Map集合
        • let m = new Map();
      • 使用set添加元素 //注 : 下方使用的 m 是在上一行声明的变量
        • m.set('name','尚硅谷'); 键为name 值为尚硅谷
        • m.set('jiayi',function(){ console.log('增加一个')}) 键为jiayi 值为fun函数
        • m.set(key,['北京','上海','深圳'])
      • m.size 返回数组中的元素数量
      • m.delete('name') 删除Map集合中的属性 删除在小括号中输入的 键 名的对象
      • m.get(key) 获取 返回值是key这个键的值 【'北京','上海','深圳'】
      • m.clear() 清空Map集合
      • 使用for...of... 遍历返回的是键值对的形式
        • for(let v of m){console.log(v)}
  • class 类
    • ES6提供了更接近传统语言的写法 引入了Class(类) 这个概念 作为对象的模板 通过class关键字 可以定义类 基本上ES6的class可以看做只是一个语法糖 他绝大部分功能 ES5都可以做到 新的class写法 只是让对象原型的写法更加清晰 更像面向对象变成的语法而已
    • 创建class类
      • class 类名{ constructot(形参1,形参2){this形参1 = 形参1;this形参2 = 形参2;} fun(){console.log(‘我是一个方法’)} }
      • let 变量 = new 类名(实参1,实参2)
      • 调用类 console.log(变量) 类名.fun() 调用方法
    • 子类的继承

      ES6新增_第24张图片

      • 如果在子类中创建了一个和父类同名的方法 则该方法会在子类中继承的父类方法进行替换 子类调用这个同名方法的时候 调用的是子类中的同名方法
  • get和set
    • get 当该方法被访问的时候 该方法就会被触发

      ES6新增_第25张图片

    • set 当该方法被修改的时候会被触发

      ES6新增_第26张图片

  • 数值的扩展
    • 0)Number.EPSILON 是JavaScript表示的最小精度
      • EPSILON属性的值接近于 2.2204460492503130808472633361816E-16
    • 1)Number.isFinite(数字) 判断一个数是否是一个有限数字 如果是就返回为true
    • 2)Number.isNaN(数字) 判断一个数字是不是一个非数字类型
    • 3)Number.parseInt(参数) Number.parseFloat(参数) 可以将字符串转换成数字 将参数中的非数字的字母删除只保留数字和.
    • 4)Number.isInteger(参数) 判断一个数是否为整数
    • 5)Math.trunc(参数) 将数字的小数部分摸出 只保留整数
    • 6)math.sign(参数) 判断参数是 正数 负数 还是0 如果是正数则返回为1 如果是负数返回为-1 如果是0则返回为0
  • 对象扩展的方法
    • Object.keys(对象) 获得对象的所有属性名 返回数组
    • Object.create(对象) 创建对象 如果写参数 则以参数创建对象 如果不写则创建一个空对象
    • Object.getPrototypeOf(对象) 获得对象原型
    • Object.getOwnPropertyNames(对象) 获得对象的所有属性名
    • Object.getOwnPropertySymbols(对象) 获得对象的所有Symbol 符号
    • Object.getOwnPropertyDescriptor(对象,“name”) 获得属性的描述
    • Object.is(参数1,参数2) 判断对象是不是唯一对象 判断对象是不是同一内存地址 如果是返回为true
    • Object.assign(参数,参数2) 将给定参数转换成一个对象 如果放入多个参数 则将所有参数合并成一个对象 如果添加的有对象 则原数组改变 如果有多个用逗号隔开
    • Object.seal(对象) 密封对象 不能添加新属性 密封对象不可配置 但是可以修改
    • Object.isSealend(对象) 判断是否密封
    • Object.freeze(对象) 冻结对象 只读状态 不可配置不能修改 只可以查看
    • Object.isFrozen(对象) 判断是否冻结
  • ES6模块化
    • 模块化是指将一个大的程序文件 拆封成许多小的文件 然后将小文件组合起来
    • 模块化的好处
      • 1)防止命名冲突
      • 2)代码复用
      • 3)高维护性
    • export 导出数据 想要导出数据 只需要在想要导出的数据前方添加export
      • 例 export function teach(){console.log('aaaaaa')}
      • 也可以将变量名放入一个对象中 在对象前添加 export {a,b,c} 这样就可以一次性导出3个对象
    • import 导入数据 如果在html界面导入 \
      • 通用导入方式
        • //all是一个变量名可以随便起 这个方法是接收这个文件夹所有导出的数据
          • 读取这个文件导出了哪些方法只需要打印 as 后方的变量名就可以了
      • export default{} 默认导出 在default 中的数据 都会被导出 为一个object对象 如果想要获取其中的数据 需要在default中在深入一层 就比如访问一个name属性就需要 all.default.name
        • 在一个文件中只可以有一个default属性 该属性不能被重复使用 export没有这个限制 可以无限次使用

          ES6新增_第27张图片

      • 解构赋值形式导入
        • import{school,teach} from '路径'
        • import{school as abc,teach} from '路径' 如果两个名字一样的情况下 就可以使用as给键名设置一个别名 这样就可以解决变量名重复的问题
        • import{default as cba} from '路径' 再导入default默认导出的暴露的方法的时候 必须要使用as给default 设置一个别名 不然无法使用 个人感觉是因为每个文件都可以有一个default方法 给别名之后就可以更好地区分 避免变量名重复问题
      • 简便形式 针对默认暴露
        • import 变量 from "路径" console.log(变量) 只可以将默认暴露的数据获取

          ES6新增_第28张图片

    • 将模块导入到js中 在html文档中只引用一个 js文件就可以使用其他文件中导出的模块 兼容性不是很好 一般会使用babel先转换一下在引用

      ES6新增_第29张图片

  • 绿字为注释 红字为自定义的 篮字必写在在调试终端中输入 黑字在html或js页面中输入
  • 将ES6中书写的代码转换成ES5中可识别的文件
    • 1 安装工具 babel-cli babel-preset-env browserify -D (webpack) //-D是开发依赖
    • 2 局部安装babel npx babel src/js(选择安装的文件夹) -d disrt/js(转换完成要存入的文件夹) --preset=babel-preset-env(预设) 如果想要全局安装输 babel
    • 3 打包 npx browserify dist/js/app.js(入口文件) -o dist/bundle.js (在啊dist文件目录下生成一个bundle.js文件 用来存储打包数据)
    • 打包完成后再html页面 使用script引入生成出来的打包文件就可以了
  • 安装jquer包 npm i jquery 在想要安装的文件夹中输入
    • import $ from 'jquer' //导入文件包 和 const $ = require("jquery") 一样
    • $('boby').css('backgound','pink'); //将页面颜色变成粉色 如果不安装 bable 的话浏览器识别不了
    • 局部安装babel npx babel src/js(选择安装的文件夹) -d disrt/js(转换完成要存入的文件夹) --preset=babel-preset-env(预设)
    • 打包 npx browserify dist/js/app.js(入口文件) -o dist/bundle.js (在啊dist文件目录下生成一个bundle.js文件 用来存储打包数据) 打包转化

你可能感兴趣的:(javascript,开发语言,ecmascript)