目錄
2.6 Symbol
2.7 Map 和 Set
2.8 迭代器和生成器
2.9 Promise對象
2.10 Proxy對象
2.11 async的用法
2.22 類class
2.23 模塊化實(shí)現(xiàn)
2.6 Symbol
? ? ? ? 原始數(shù)據(jù)類型,它表示是獨(dú)一無二的值。它屬于 JavaScript 語言的原生數(shù)據(jù)類型之一,其他數(shù)據(jù)類型是:undefined
、null
、布爾值(Boolean)、字符串(String)、數(shù)值(Number)、大整數(shù)(BigInt)、對象(Object)。
? ? ? ? Symbol值通過Symbol() 函數(shù)生成。
? ? ? ? 最大的用途:用來定義對象的私有變量,用Symbol定義的對象中的變量,取值時一定要用 [變量名] 。
let s1 = Symbol('s1');
let obj = {
[s1]: '張三'
}
console.log(obj[s1]); // 張三
console.log(obj.s1); // undefined
? ? ? ? ?Symbol值作為屬性名,遍歷對象的時候,該屬性不會出現(xiàn)在for..in,for...of循環(huán)中,也不會被Object.keys()等返回。它有一個Object.getOwnPropertySymbols()方法,獲取指定對象的所有Symbol屬性名,該方法返回一個數(shù)組,成員是當(dāng)前對象的所有用作屬性名的Symbol值。
? ? ? ? 另一個API:Reflect.ownKeys() 方法,可以返回所有類型的鍵名,包括常規(guī)鍵名和 Symbol 鍵名。
let s1 = Symbol('s1');
let obj = {
[s1]: '張三',
[Symbol('s2')]: '李四',
s3: '王五'
}
// console.log(obj[s1]); // 張三
// console.log(obj.s1); // undefined
// 獲取symbol聲明的屬性名(作為對象的key)
let s = Object.getOwnPropertySymbols(obj);
console.log(s); // [Symbol(s1), Symbol(s2)]
let m = Reflect.ownKeys(obj);
console.log(m); // ['s3', Symbol(s1), Symbol(s2)]
注意:
1、Symbol() 函數(shù)不能使用new命令,否則會報錯,生成的Symbol是一個原始類型的值,不是一個對象;
2、 由于Symbol值不是對象,不能添加屬性。
2.7 Map 和 Set
一、Set 集合
1、Set 集合:表示一個無重復(fù)值的有序列表,類似于數(shù)組,本身是一個構(gòu)造函數(shù),用來生成Set數(shù)據(jù)結(jié)構(gòu)。
let set = new Set();
console.log(set);
?2、方法:
1)添加元素
set.add(2);
set.add('4');
set.add('4');
set.add([1,2,3]);
console.log(set); // {2, "4", [1,2,3]}
2)刪除元素
// 刪除元素
set.delete(2);
console.log(set); //{ "4", [1,2,3]}
3)校驗(yàn)?zāi)硞€值是否在set中,存在true,不存在false
console.log(set.has('4')); //true
4)集合的長度
console.log(set.size); //2
?5)將set集合轉(zhuǎn)化為數(shù)組
// 將set轉(zhuǎn)換成數(shù)組
let set2 = new Set([1,1,2,3,3,4,5,5]);
let arr = [...set2];
console.log(arr); // [1, 2, 3, 4, 5]
6)清除所有成員,沒有返回值
set.clear();
7)WeakSet? ? ??
? ? ? ? WeakSet結(jié)構(gòu)與Set類似,也是不重復(fù)的值的集合??梢杂糜趦Υ鍰OM節(jié)點(diǎn),而不用擔(dān)心這些節(jié)點(diǎn)從文檔移除時會引發(fā)內(nèi)存泄漏。
? ? ? ? (1)WeakSet 的成員只能是對象,而不能是其他類型的值;
? ? ? ? (2)WeakSet 中的對象都是弱引用;
? ? ? ? (3)不可迭代;
? ? ? ? (4)沒有forEach();
? ? ? ? (5)沒有size屬性。
let set3 = new WeakSet(), obj = {};
set3.add(obj);
// 釋放當(dāng)前的資源
obj = null;
console.log(set3);
二、Map 類型
????????Map類型是鍵值對的有序列表,鍵和值是任意類型,類似于對象。
let map = new Map();
map.set('name','張三');
map.set('age',20);
console.log(map); // {'name' => '張三', 'age' => 20}
console.log(map.get('name')); // 張三
map.has('name'); // true
map.delete('name');
console.log(map); //{'age' => 20}
map.clear();
console.log(map); //{size: 0}
map.set(['a',[1,2,3]],'hello');
console.log(map); //{Array(2) => 'hello'}
let m = new Map([['a',1],['c',2]]);
console.log(m); //{'a' => 1, 'c' => 2}
?遍歷方法:
1、.keys()? 返回鍵名的遍歷器
2、.values() 返回鍵值的遍歷器
3、.entries() 返回所有成員的遍歷器
4、.forEach() 遍歷Map的所有成員
let m = new Map(
[
['A',1],
['B',2]
]
)
for(let key of m.keys()){
console.log(key);
}
// A
// B
for(let val of m.values()){
console.log(val);
}
// 1
// 2
for(let item of m.entries()){
console.log(item);
console.log(item[0],item[1]);
}
// ['A', 1]
// A 1
// ['B', 2]
// B 2
m.forEach((val,key,map)=>{
console.log(val,key,map);
})
// 1 'A' {'A' => 1, 'B' => 2}
// 2 'B' {'A' => 1, 'B' => 2}
?.forEach() 方法可以接受第二個參數(shù),用來綁定this
const reporter = {
report: function(key, value) {
console.log("Key: %s, Value: %s", key, value);
}
};
m.forEach(function(value, key, map) {
this.report(key, value);
}, reporter);
// Key: A, Value: 1
// Key: B, Value: 2
?Map 結(jié)構(gòu)轉(zhuǎn)為數(shù)組結(jié)構(gòu),使用擴(kuò)展運(yùn)算符
let m0 = new Map([
[1,'one'],
[2,'two'],
[3,'three']
]);
console.log([...m0.keys()]); //[1, 2, 3]
console.log([...m0.values()]); //['one', 'two', 'three']
console.log([...m0.entries()]); //[[1,'one'], [2, 'two'], [3, 'three']]
console.log([...m0]); //[[1,'one'], [2, 'two'], [3, 'three']]
2.8 迭代器和生成器
一、 Iterator 迭代器
? ? ? ? 一種新的遍歷機(jī)制,兩個核心:
1. 迭代器是一個接口,能快捷的訪問數(shù)據(jù),通過Symbol.iterator來創(chuàng)建迭代器,通過迭代器的next() 獲取迭代之后的結(jié)果;
2. 迭代器是用于遍歷數(shù)據(jù)結(jié)構(gòu)的指針(數(shù)據(jù)庫的游標(biāo))。
const items = ['one','two','three','four'];
const ite = items[Symbol.iterator]();
console.log(ite.next()); //{value: 'one', done: false} done如果為false表示遍歷繼續(xù),如果為true表示遍歷完成
console.log(ite.next()); // {value: 'two', done: false}
console.log(ite.next()); // {value: 'three', done: false}
console.log(ite.next()); // {value: 'four', done: false}
console.log(ite.next()); // {value: undefined, done: true}
二、生成器 Generator?
? ? ? ? 可以通過yield關(guān)鍵字,將函數(shù)掛起,為改變執(zhí)行流程提供了可能,同時為做異步編程提供了方案。
? ? ? ? 與普通函數(shù)的區(qū)別:
? ? ? ? 1. function 后面,函數(shù)名之前有個 * ;
? ? ? ? 2. 只能在函數(shù)內(nèi)部使用 yield 表達(dá)式,讓函數(shù)掛起。
function* func(){
yield 2;
yield 3;
}
// 返回一個遍歷器對象,可以調(diào)用next()
let fn = func();
console.log(fn.next());//{value: 2, done: false}
console.log(fn.next());//{value: 3, done: false}
console.log(fn.next());//{value: undefined, done: true}
// generator函數(shù)是分段執(zhí)行的,yield語句是暫停執(zhí)行,而next() 是恢復(fù)執(zhí)行
function* add(){
let x = yield '2';
// x 不是yield '2'的返回值,它是next() 調(diào)用,恢復(fù)當(dāng)前 yield 執(zhí)行傳入的實(shí)參
console.log("one:",x);
let y = yield '3';
console.log("two:",y);
return x+y;
}
const fn = add();
console.log(fn.next()); // {value: '2', done: false}
console.log(fn.next(20)); // {value: '3', done: false}
console.log(fn.next(30)); // {value: 50, done: true}
// 使用場景:為不具備Interator接口的對象提供了遍歷的操作
function* objectEntries(obj){
// 獲取對象所有的key保存到數(shù)組
const propKeys = Object.keys(obj);
for(const propkey of propKeys){
yield [propkey,obj[propkey]]
}
}
const obj = {
name: '張三',
age: 18
}
obj[Symbol.iterator] = objectEntries;
console.log(obj);
for(let [key,value] of objectEntries(obj)){
console.log(`${key}:${value}`);
}
//name:張三
//age:18
2.9 Promise對象
一、介紹
????????Promise 是異步編程的一種解決方案,它由社區(qū)最早提出和實(shí)現(xiàn),ES6 將其寫進(jìn)了語言標(biāo)準(zhǔn),統(tǒng)一了用法,原生提供了Promise對象。
????????相當(dāng)于一個容器,保存著未來才會結(jié)束的事件(異步操作)的一個結(jié)果。
????????各種異步操作都可以用同樣的方法進(jìn)行處理 axios。
特點(diǎn):
1、對象的狀態(tài)不受外界影響,處理異步操作三個狀態(tài):pending(進(jìn)行中)、fulfilled(resolved)(成功)、rejected(失?。?。
2、pending(進(jìn)行中)、fulfilled(resolved)(成功)、rejected(失敗)一旦狀態(tài)改變,就不會再變,任何時候都可以得到這個結(jié)果。
let pro = new Promise(function(resolved,rejected){
// 執(zhí)行異步操作
});
console.log(pro);
?二、基本使用
let pro = new Promise(function(resolved,rejected){
// 執(zhí)行異步操作
let res = {
//code: 200,
code: 201,
data:{
name: '張三',
age: 20
},
error:'失敗了!'
}
setTimeout(()=>{
if(res.code == 200){
resolved(res.data);
}else{
rejected(res.error);
}
},1000)
});
console.log(pro);
// then()方法
// 第一個參數(shù)是resolve回調(diào)函數(shù),第二個參數(shù)是可選的,是reject狀態(tài)回調(diào)函數(shù)
// 返回的是一個新的promise實(shí)例,可以采用鏈?zhǔn)骄幊?pro.then((val)=>{
console.log(val); //{name: '張三', age: 20}
},(err)=>{
console.log(err); //失敗了!
})
const pro = new Promise(function(resolve,reject){
throw new Error('test');
})
pro.catch(function(err){
console.log(err); //Error: test
})
const promise = new Promise(function(resolve, reject) {
try {
throw new Error('test');
} catch(e) {
reject(e);
}
});
promise.catch(function(error) {
console.log(error);
});
方法:
1、resolve() 能將現(xiàn)有的任何對象轉(zhuǎn)換成promise對象
let p = Promise.resolve('foo');
let p1 = new Promise(resolve => resolve('foo'));
console.log(p);
console.log(p1);
?2、reject() 同resolve()方法
3、all()?用于將多個 Promise 實(shí)例,包裝成一個新的 Promise 實(shí)例。
const p = Promise.all([p1, p2, p3]);
?1)p1、p2、p3都是Promise實(shí)例,如果不是,會先調(diào)用Promise.resolve()方法,將參數(shù)轉(zhuǎn)為Promise實(shí)例,再進(jìn)一步處理。參數(shù)可以不是數(shù)組,但必須具有Iterator接口,且返回的每個成員都是Promise實(shí)例。
2)只有三個參數(shù)p1、p2、p3的狀態(tài)都變成fulfilled,p的狀態(tài)才會變成fulfilled,三參的返回值組成一個數(shù)組,傳遞給p的回調(diào)函數(shù)。
3)三參中只要有一個rejected,p的狀態(tài)就是rejected,此時第一個被reject的實(shí)力的返回值傳遞給p的回調(diào)函數(shù)。
4)多應(yīng)用與游戲霍素材比較多時,等待圖片、falsh、靜態(tài)資源文件都加載完成,才進(jìn)行頁面的初始化。
4、race() 給某個異步請求設(shè)置超時時間,并且在超時后執(zhí)行相應(yīng)的操作
function requestImg(imgSrc){
return new Promise((resolve,reject)=>{
const img = new Image();
img.onload = function(){
resolve(img);
}
img.src = imgSrc;
})
}
function timeout(){
return new Promise((resolve,reject)=>{
setTimeout(()=>{
reject(new Error('圖片請求超時'));
},3000)
})
}
Promise.race([requestImg('img.png'),timeout()]).then(data=>{
console.log(data);
document.body.appendChild(data);
}).catch(err=>{
console.log(err); //Error: 圖片請求超時
})
5、finally()?用于指定不管 Promise 對象最后狀態(tài)如何,都會執(zhí)行的操作。該方法是 ES2018 引入標(biāo)準(zhǔn)的。
2.10 Proxy對象
一、介紹
????????用于修改某些操作的默認(rèn)行為,等同于在語言層面做出修改,所以屬于一種“元編程”(meta programming),即對編程語言進(jìn)行編程。
????????在目標(biāo)對象之前架設(shè)一層“攔截”,外界對該對象的訪問,都必須先通過這層攔截,因此提供了一種機(jī)制,可以對外界的訪問進(jìn)行過濾和改寫。Proxy 這個詞的原意是代理,用在這里表示由它來“代理”某些操作,可以譯為“代理器”。
二、方法
1、get() 用于攔截某個屬性的讀取操作
var proxy = new Prosy({},{
// target - 目標(biāo)對象; propKey - 屬性名;proxy實(shí)例本身,可選
get:function(target,propKey,[proxy]){
}
});
2、set() 用來攔截某個屬性的賦值操作,接收四個參數(shù):目標(biāo)對象、屬性名、屬性值和proxy實(shí)例本身,最后一個參數(shù)可選。?
2.11 async的用法
一、async 異步操作
????????作用:使得異步操作更加方便。
????????基本操作 async 返回一個Promise對象 ?
????????async是Genterator的一個語法糖
async function f(){
// await不能單獨(dú)使用,必須要在async中
// return await 'hello async';
let s = await 'hello async';
let data = await s.split('');
return data;
}
// 如果async函數(shù)中有多個await 那么then函數(shù)會等待所有的await指令執(zhí)行完的結(jié)果才去執(zhí)行
f().then(v=>console.log(v)).catch(e=>console.log(e));
// ['h', 'e', 'l', 'l', 'o', ' ', 'a', 's', 'y', 'n', 'c']
async function f2(){
// throw new Error('出錯了');
await Promise.reject('出錯了');
await Promise.resolve('hello');
}
// 只要有一個await命令進(jìn)入reject就不會繼續(xù)執(zhí)行
f2().then(v=>console.log(v)).catch(e=>console.log(e)); // 出錯了
?如果想要繼續(xù)執(zhí)行,修改代碼如下:
async function f2(){
// throw new Error('出錯了');
try {
await Promise.reject('出錯了');
} catch (error) {
}
return await Promise.resolve('hello');
}
// 只要有一個await命令進(jìn)入reject就不會繼續(xù)執(zhí)行
f2().then(v=>console.log(v)).catch(e=>console.log(e)); // hello
2.22 類class
? ? ? ? 通過class關(guān)鍵字,可以定義類,是一個語法糖。
class Person{
// 實(shí)例化的時候會立即被調(diào)用
constructor(name,age){
this.name = name;
this.age = age;
}
// sayName(){
// return this.name;
// }
// sayAge(){
// return this.age;
// }
}
// 通過Object.assign()方法一次性向類中添加多個方法
Object.assign(Person.prototype,{
sayName(){
return this.name;
},
sayAge(){
return this.age;
}
})
let p1 = new Person('張三',20);
console.log(p1);
console.log(p1.sayName()); // 張三
console.log(p1.sayAge()); // 20
?類的繼承
// 使用關(guān)鍵字extends
class Animal{
constructor(name,age){
this.name = name;
this.age = age;
}
sayName(){
return this.name;
}
sayAge(){
return this.age;
}
}
class Dog extends Animal{
constructor(name,age,color){
super(name,age); // 相當(dāng)于Animal.call(this,name,age);
this.color = color;
}
// 子類自己的方法
sayColor(){
return `${this.name},${this.age}個月,顏色是${this.color}`;
}
// 重寫父類的方法
sayName(){
return this.name + super.sayAge() + this.color;
}
}
let dog = new Dog('杜賓',12,'black');
console.log(dog); //{name: '杜賓', age: 12, color: 'black'}
console.log(dog.sayName()); // 杜賓
console.log(dog.sayColor()); //杜賓,12個月,顏色是black
console.log(dog.sayName()); //杜賓12black
2.23 模塊化實(shí)現(xiàn)
????????ES6 module 兩個命令構(gòu)成:export 和 import
????????export 用于規(guī)定模塊的對外接口,import用于輸入其他模塊提供的接口
????????一個模塊就是一個獨(dú)立的文件
index.js文章來源:http://www.zghlxwxcb.cn/news/detail-563485.html
export const name = '張三';
export const age = 18;
// 函數(shù)拋出在函數(shù)前面增加export
export function sayName(){
return 'my name is 哈哈哈';
}
// 或拋出一個對象
function sayAge(){
return 19;
}
export {sayAge}
class Person{
constructor(){
}
sayColor(){
console.log("red");
}
}
export default Person;
1.html文章來源地址http://www.zghlxwxcb.cn/news/detail-563485.html
<script type="module">
import Person,{name,age,sayName,sayAge} from './index.js';
console.log(name,age,sayName(),sayAge()); // 張三 18 my name is 哈哈哈 19
const p = new Person();
p.sayColor(); //red
</script>
路漫漫其修遠(yuǎn)兮,吾將上下而求索!
到了這里,關(guān)于ECMAScript 6 之二的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!