let
1、使用let声明变量,只能在代码块内有效
{
let a = 1;
consolse.log(a)//1
}
2、使用let声明的变量,在预解析的时候不会被提升
{
console.log(a);//undefined
var a = 1;
}
{
console.log(a);//报错
let a = 1;
}
3、let不允许在同一个作用域下声明已经存在的变量
{
<!--报错-->
var a = 1;
let a = 2;
}
const
1、const声明常量,常量值不能改变,声明的时候必须赋值
{
const a = 1;
conlose.log(a);//12
}
2、基本数据类型
{
var a = 1;
var b = a;
b = 2;
console.log(a);//1
}
3、引用数据类型
{
var a = {attr:1};
var b = a;
b.attr = 2;
console.log(a.attr);//2
}
{
const a = {b:1};
a.b = 2;
console.log(a);//{b:2}
}
set
1、ES6提供的一个新的数据结构,它类似于数组,但是成员的值都是唯一的,没有重复的值。
set本身是一个构造函数,用来生成set数据结构
{
let s = new Set([1,2,3);
console.log(s);//输出set()数组
console.log(s.size)//输出set数组的长度
}
2、添加
{
let s = new Set([1,2,3);
s.add('a').add('b').add('c');
console.log(s);//添加a,b,c
}
3、删除
{
let s = new Set([1,2,3);
console.log(s.delete('a'));//删除a
console.log(s)
}
4、has()包含,判断该值是否为set的成员,返回的是一个boolean
{
let s = new Set([1,2,3]);
console.log(s.has('a')//false
}
5、clear()清除所以数据,没有返回值
{
let s = new Set([1,2,3]);
s.clear();
console.log(s);//set(0)
}
6、key和values
{
let s = new Set([1,2,3]);
console.log(s.key());
consloe.log(s.values());//返回整个数组的key和value值
}
7、entries将对象转为Map格式entries
{
let s = new Set([1,2,3]);
console.log(s.entries())
}
8、forEach
{
let s = new Set([1,2,3]);
s.forEach(function(value,key,set){
console.log(set)
}
}
解构赋值
1、解构赋值
let [a,b,c] = [1,2,3];
console.log(a,b,c)//1 2 3
}
2、空数组解构不成功
{
let [a] = [];
console.log(a);//undefined
console.log(typoef null)//object
}
3、字符串会被解析成类数据
{
let [a,b,c,d]= '1234';
let {length:len} = '123456'
console.log(len);//6
}
4、null和undefined不能被解构赋值
let [a] = undefind;
console.log(a)//报错
}
掌握es6的应用
(一).ES6中的模块
ES6 模块的设计思想是尽量的静态化,使得编译时就能确定模块的依赖关系
一个文件就是一个模块,想让外部能使用这个变量就必须export变量
1).模块的导出和模块的导入
模块导入会导致变量提升,并且import语句只能用在最顶层作用域上。
export let a = 1; // export导出的是接口不是具体的值 import * as obj from './a.js'; import {a} from './a.js';
2).模块的动态绑定
let obj = 1; setInterval(()=>{obj++;},1000) // 外部使用这个变量也会发生变化 export { obj };
3).模块导出的命名问题
export { a as default, b, } import _,* as obj from './a.js'; console.log(_,obj); _ = '不能修改变量'
4).模块的默认导出
export default a // 只是导出的时候给a重命名为default而已,default后面导出的都是具体的值 export { b, }
5).导入模块并导出
export let a = 1; export {obj} from './b.js'; // 当前模块下并不能使用obj这个值
6).import 动态导入语法
import('./a.js').then(data=>{ console.log(data.default); });
(二).ES6中的类
在es6之前生成实例对象是通过构造函数的方式,在es6中提供了类
构造函数类的继承方式
Animal.call(this) Tiger.prototype.__proto__ = Animal.prototype; Object.setPrototypeOf(Tiger.prototype,Animal.prototype) Tiger.prototype = Object.create(Animal.prototype,{constructor:{value:Tiger}}); Tiger.prototype = new Animal();
1).new.target用法
class Animal { constructor(){ if(new.target === Animal){ throw new Error('不能实例化动物类'); } } eat(){ console.log('吃饭') } } class Tiger extends Animal{} let animal = new Animal(); animal.eat();
2).类的访问器用法
class Tiger extends Animal{ constructor(){ super(); this._age = 10; } get age(){ return this._age; } set age(val){ this._age = val; } } let tiger = new Tiger();
3).静态方法和静态属性
class Animal { eat(){ console.log('吃饭') } static type(){ return '哺乳类' } static get MyKind(){ return '老虎' } } class Tiger extends Animal{ } console.log(Tiger.MyKind);
4).super的应用
class Animal { eat(){ console.log('吃饭') } static type(){ return '哺乳类' } } class Tiger extends Animal{ constructor(){ super();// 指代的是父类 } static getType(){ return super.type(); // 指代的是父类 } eat(){ super.eat(); // 指代的是父类原型对象 } } let tiger = new Tiger(); console.log(Tiger.getType()); console.log(tiger.eat());
5).装饰器的应用
装饰器最终需要返还一个函数
@log1() @log2() class MyClass{} function log1(){ console.log('outer1') return function(target){ // 装饰类指代的是当前类本身 console.log('inner1'); } } function log2(){ console.log('outer2') return function(){ console.log('inner2'); } }
6)修饰类中原型上的方法
class MyClass{ @enumerable(false) // 是否可枚举 getName(){ return 'hello'; } } function enumerable(boolean){ return function(target,key,descriptor){ //value.enumerable = true; return { ...descriptor, enumerable:boolean, } } }
7.)修饰类中实例的属性
class MyClass{
@readonly PI = 3.14
}
function readonly(target,key,value){
value.writable = false;
}
let my = new MyClass();
my.PI = 3.15;
console.log(my.PI)