Understanding ES6学习笔记

Chapter 1
let: 
1.不能进行变量提升,所以变量一定要在声明后使用。
2.只在let所在的块内起作用。
3.let不允许在相同作用域内,重复声明同一个变量。在不同的作用域则可以。
4.ES5只有全局作用域和函数作用域,可能造成一些问题,如内层变量覆盖外层变量、for循环用来计数的循环变量泄露为全局变量等。let实际上为JavaScript新增了块级作用域。

const:
1.一经定义,不得改变,也不能进行变量提升,在声明的时候一定要进行初始化,否则会报错。
2.也是在块内起作用
3.若const储存的是一个地址,这个地址指向一个对象。不可变的只是这个地址,即不能把它指向另一个地址,但对象本身是可变的,所以依然可以为其添加新属性。

暂时性死区:

如果区块中存在let和const命令,这个区块对这些命令声明的变量,从一开始就形成了封闭作用域。凡是在声明之前就使用这些变量,就会报错。


Chapter 4
对象扩展
对象字面量扩展
1.创建对象时,当属性名和变量名相等时,省略属性名
function createPerson(name, age) {
    return {
        name,
        age
    };
}
2.给对象添加方法时,省略function
var person = {
    name: "Nicholas",
    sayName() {
        console.log(this.name);
    }
};
3.属性名
let lastName = "last name";
let person = {
    "first name": "Nicholas",
    [lastName]: "Zakas"
};
console.log(person["first name"]);      // "Nicholas"
console.log(person[lastName]);          // "Zakas"
用表达式作为属性名:
var suffix = " name";
var person = {
    ["first" + suffix]: "Nicholas",
    ["last" + suffix]: "Zakas"
};
console.log(person["first name"]);      // "Nicholas"
console.log(person["last name"]);       // "Zakas"
4.新方法
1.Object.is()  比较两个值是否严格相等
2.Object.assign()  用于对象的合并,将源对象的所有属性复制到目标对象
var target = { a: 1 };
var source1 = { b: 2 };
var source2 = { c: 3 };
Object.assign(target, source1, source2);
target // {a:1, b:2, c:3}
还可用于为对象添加属性、方法等。
5.重写
"use strict";
var person = {
    name: "Nicholas",
    name: "Greg"        // no error in ES6 strict mode
};
console.log(person.name);       // "Greg"
6.属性枚举顺序 Object.getOwnPropertyNames(obj)
数字按升序排列,字符串按它们添加到对象的顺序排列.
7.改变Prototype
Object.setPrototypeOf()方法,接收两个对象最为参数
8.super 指向当前对象原型的指针
原为Object.getPrototypeOf(this).getGreeting.call(this);
改为super.getGreeting();
【在简化的方法中】,可以通过super调用对象原型上的任何方法。
let friend = {
    getGreeting: function() {
        // syntax error
        return super.getGreeting() + ", hi!";
    }
};



Chapter 5
解构赋值
ES6允许按照一定模式,从数组和对象中提取值,对变量进行赋值。
1.对象解构
let node = {
    type: "Identifier",
    name: "foo"
};
let { type, name } = node;
变量名和属性名一致
var { foo, bar } = { foo: "aaa", bar: "bbb" };
foo // "aaa"
bar // "bbb"
对象的解构赋值的内部机制,是先找到同名属性,然后再赋给对应的变量。真正被赋值的是后者,而不是前者。
var { foo: baz } = { foo: "aaa", bar: "bbb" };
baz // "aaa"
foo // error: foo is not defined
也可嵌套
var obj = {
  p: [
    'Hello',
    { y: 'World' }
  ]
};
var { p: [x, { y }] } = obj;
x // "Hello"
y // "World"
指定默认值
let node = {
    type: "Identifier",
    name: "foo"
};
let { type, name, value = true } = node;
2.数组解构
数据解构对items的位置操作
模式匹配
let colors = [ "red", "green", "blue" ];
let [ firstColor, secondColor ] = colors;
console.log(firstColor);        // "red"
console.log(secondColor);       // "green"
交换变量:
let a = 1,
    b = 2;
[ a, b ] = [ b, a ];
3.混合


Chapter 7
1.set:
类似数组,但成员的值唯一
let set=new Set();
可接收一个数组作为参数,用来初始化。
添加:set.add(value)
判断是否存在:set.has(value)
删除一个:set.delete(value)
删除全部:set.clear() 
forEach()方法:set.forEach(function(value,key,ownerSet){});forEach方法还可以有第二个参数,表示绑定的this对象。
key和value相等
set里的forEach()不能访问items索引,如需要,则应将其转换为数组。
Array.from方法可将Set结构转换为数组。
set转换为array: array=[...set];(会去除set中的重复项)。
Weak Sets:(对象引用)弱引用
(即垃圾回收机制不考虑WeakSet对该对象的引用,也就是说,如果其他对象都不再引用该对象,那么垃圾回收机制会自动回收该对象所占用的内存,不考虑该对象还存在于WeakSet之中。这个特点意味着,无法引用WeakSet的成员,因此WeakSet是不可遍历的。)
WeakSet结构与Set类似,也是不重复的值的集合,但WeakSet的成员只能是对象。
创建:
let set=new WeakSet();
三大集合对象:arrays, maps, sets

2.map:(key-value)
let map=new Map();
添加:map.set(key,value);
检索:map.get();
对象也可以是key。
也有has(),delete(),clear()方法。
Weak Maps:
每一个key都必须是对象object,键名所指向的对象,不计入垃圾回收机制。
用处:和DOM元素进行数据交互。存储对象实例的专用数据。
(WeakMap的设计目的在于,键名是对象的弱引用(垃圾回收机制不将该引用考虑在内),所以其所对应的对象可能会被自动回收。当对象被回收后,WeakMap自动移除对应的键值对。典型应用是,一个对应DOM元素的WeakMap结构,当某个DOM元素被清除,其所对应的WeakMap记录就会自动被移除。基本上,WeakMap的专用场合就是,它的键所对应的对象,可能会在将来消失。WeakMap结构有助于防止内存泄漏。)


Chapter 8
1.是一个方法,返回一个迭代器。function关键字与函数名之间有一个星号,函数体内部使用yield语句,定义不同的内部状态。
2.function *createIterator(){}
let iterator=createIterator();  指向内部状态的指针对象
如果是匿名函数,星号的位置为:
let createIterator=function *(){}
3.yield:执行完一条时,暂停执行,直到下一个next()调用的时候,再执行下一条yield。每次调用next(),返回一个有着value和done两个属性的对象。
4.因为是方法,可添加到对象。
5.for-of
如果只是迭代数组或集合里的值的话用for-of
let values=[1,2,3];
for(let num of values){
    console.log(num);
}
6.通过Symbol.iterator访问默认迭代器
let values=[1,2,3];
let iterator=values[Symbol.iterator]();
console.log(iterator.next());
获取默认迭代器,并用于遍历数组中的items,也是for-of的内部过程。
还可以据此判断一个对象是否可迭代。
7.自定义迭代器
自己创建一个Symbol.iterator属性,该属性包含一个Generator函数。
8.内置迭代器
entries() 返回key-value对
values() 返回values
keys() 返回keys
9.三大集合类型的for-of时的默认迭代器
arrays/sets: values()
maps: entries()
10.字符串迭代器
for-of 可打印字符串的双字节字符
11. 节点列表迭代器
12.扩展运算符(...)
可将多个数组插入到一个数组中
13.高级迭代器功能
当将参数传递给next()方法时,该参数将成为上一个yield语句的返回值。
iterator.throw(new Error("boom"));
使用yield时,next()和throw()方法控制迭代器中的执行。next()可通过给定值来指示迭代器继续执行,throw()通过抛出错误来指示迭代器继续执行。
14. return 停止执行,done为true,value为undefined。若提供一个返回值,则value为该值,done为true。再执行一条next()时,value变为undefined。
15. 委托
在yield和函数名之间加*号,可以委托给别的Generator。
function *createCombinedIterator(){
    yield *createNumberIterator();
    yield *createColorIterator();
}
据此可以将多个Generator的value合成一个。
也可访问返回值。
16. 异步编程
因为生成器允许在执行的时候有效地暂停执行,这位异步处理提供了许多可能性。
一个简单的任务运行器,需定义一个函数,接受一个Generator作为参数,在函数内创建一个迭代器并start。
若要传递数据,可将result.value传入next()作为参数。
一个异步的任务运行器,result.value(function(err,data){} 有一个回调函数。


Chapter 9

1.类的声明:
class PersonClass{
    constructor(name){
        this.name=name;
    }
    sayName(){
         console.log(this.name);
    }
}
let person=new PersonClass("Jack");
2.类的声明类似let,存在暂时性死区。
3.在类的里面不能重写类名,在类外可以。
4.类表达式
匿名类表达式,省略类名。let PersonClass=class{}
若有类名,如let PersonClass=class PersonClass2{},则PersonClass2只存在于类内,类外为undefined。
5.ES6中,类可作为函数参数。
6.类表达式可通过立即调用类构造函数来创建实例。需要new。
let person=new Class{
    constructor(name){
        this.name=name;
    }
    sayName(){
        console.log(this.name);
    }
}("Jack");
创建一个匿名类表达式并立即执行。
7.访问器属性
类允许在原型上定义访问器属性。get和set
class CustomHTMLElement{
    constructor(element){
        this.element=element;
    }
    get html(){
        return this.element.inerHTML;
    }
    set html(vlaue){
        this.element.innerHTML=vlaue;
    }
}
var descriptor=Object.getOwnPropertyDescriptor(CustomHTMLElement.prototype,"html");
console.log("get" in descriptor);  //ture


【Object.getOwnPropertyDescriptor(object,propertyname)获取指定对象的自身属性描述符。自身属性描述符是指直接在对象上定义(而非从对象的原型继承)的描述符。】
8.[表达式]使用变量为类定义中的方法分配名称。
let methodName="sayName";
class PersonClass{
    constructor(name){
        this.name=name;
    }
    [methodName](){
        cosole.log(this.name);
    }
};
使用变量为类定义中的方法分配属性名
let propertyName="html";
class CustomHTMLElement{
    ...
    get [propertyName](){...}
    ...
}
9. Generator Methods
定义:
class MyClass{
    *createIterator(){
        yield 1;
        yield 2;
    }
}
let instance=new MyClass();
let iterator=instance.createIterator();
9.静态成员
class PersonClass{
    ...
    static create(name){
        return new PersonClass(name);
    }
}
let person=PersonClass.create("Jack");
10.派生类继承,关键字extends
class Rectangle {
    constructor(length, width) {
        this.length = length;
        this.width = width;
    }
    getArea() {
        return this.length * this.width;
    }
}
class Square extends Rectangle {
    constructor(length) {
        // equivalent of Rectangle.call(this, length, length)
        super(length, length);
    }
}
var square = new Square(3);
Square构造函数使用super()来调用具有指定参数的Rectangle构造函数。如果选择不使用构造函数,在创建一个新的类的实例时,super()会被自动调用。
11.继承静态成员
如果基类具有静态成员,那么这些静态成员也可在派生类上使用。
12.表达式派生类
只要表达式带有[[Construct]]的函数和原型,就可以对任何表达式使用extend。在extends之后接受任何类型的表达式提供了强大的可能性,例如动态确定要继承的内容。



chapter 10
数组
1.创建数组
Array.of() 参数为items
2.将一个类数组转换为数组
Array.from() 参数为items,可接收一个函数作为第二个参数,每个item在该函数运行后输出。还可接收第三个参数代表this。
还可在迭代器中使用:
let numbers = {
    *[Symbol.iterator]() {
        yield 1;
        yield 2;
        yield 3;
    }
};
let numbers2 = Array.from(numbers, (value) => value + 1);
console.log(numbers2);              // 2,3,4
3.find()&findIndex()
let numbers = [25, 30, 35, 40, 45];
console.log(numbers.find(n => n > 33));         // 35
console.log(numbers.findIndex(n => n > 33));    // 2
4.fill() 
对数组items的整体或部分进行重写
5.copyWithin()
6.Typed Arrays
数组缓存区
所有类型数组的基础是数组缓冲区,它是一个可以包含指定数量字节的内存位置。
创建数组缓冲区:let buffer=new ArrayBuffer(10);
console.log(buffer.byteLength); //10
可用slice()
7.使用视图操作数组缓冲区 DataView
数组缓冲区表示内存位置,视图是用于操作该内存的接口。视图对数组缓冲区或数组缓冲区字节的子集进行操作,以一种数值数据类型读取和写入数据。
let buffer=new ArrayBuffer(10);
let view=new DataView(buffer); //所有
let view=new DataView(buffer,5,2); //部分 5,6
检索视图信息有三个,buffer,byteOffset,byteLength
8.读写数据
getInt8(byteOffset,littleEndian),
setInt8(byteOffset,value,littleEndian
视图允许在任何时间点以任何格式读取和写入,而不考虑之前数据时如何存储的。
9.创建特定类型视图
let buffer=new ArrayBuffer(10),
     view1=new Int8Array(buffer),
     view2=new Int8Array(buffer,5,2);


你可能感兴趣的:(ES6,学习笔记)