亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

js版本ES6、ES7、ES8、ES9、ES10、ES11、ES12、ES13、ES14[2023]新特性

 更新時間:2024年11月02日 14:58:04   作者:冉冉同學  
ES全稱ECMAScript,ECMAScript是ECMA制定的標準化腳本語言,本文講述Javascript[ECMAScript]版本ES6、ES7、ES8、ES9、ES10、ES11、ES12、ES13、ES14[2023]的新特性,幫助朋友們更好的熟悉和使用Javascript

ES全稱ECMAScript,ECMAScript是ECMA制定的標準化腳本語言。本文講述Javascript[ECMAScript]版本ES6、ES7、ES8、ES9、ES10、ES11、ES12、ES13、ES14[2023]的新特性,幫助朋友們更好的熟悉和使用Javascript。

JS1.1(1997)

第一版基于Netscape Navigator 3.0中實現(xiàn)的JAVASCRIPT 1.1

JS1.2(1999)

基于Netscape Navigator 4.0中實現(xiàn)的JavaScript 1.2。添加了正則表達式、更好的字符串處理、新的控制語句、Try/Catch異常處理、更嚴格的錯誤定義、數(shù)字輸出格式以及其他增強功能

ES5(2015)

1.嚴格模式

use strict

2.Object

  • getPrototypeOf,返回一個對象的原型
  • getOwnPropertyDescriptor,返回某個對象自有屬性的屬性描述符
  • getOwnPropertyNames,返回一個數(shù)組,包括對象所有自由屬性名稱集合(包括不可枚舉的屬性)
  • hasOwnProperty,給定屬性存在于對象實例中,返回 true
  • isPrototypeOf,在原型鏈中出現(xiàn)過的原型,返回 true
  • create,創(chuàng)建一個擁有指定原型和若干指定屬性的對象
  • defineProperty,為對象定義一個新屬性,或者修改已有的屬性,并對屬性重新設(shè)置 getter 和 setter,這里可以被用作數(shù)據(jù)綁定的對象劫持用途
  • defineProperties,在一個對象上添加或修改一個或者多個自有屬性,與 defineProperty 類似
  • seal,鎖定對象,阻止修改現(xiàn)有屬性的特性,并阻止添加新屬性,但是可以修改已有屬性的值
  • freeze,凍結(jié)對象,阻止對對象的一切操作和更改,凍結(jié)對象將變成只讀
  • preventExtensions,讓一個對象變得不可以擴展,也就是不能再添加新的屬性
  • isSealed,判斷對象是否被鎖定
  • isFrozen,判斷對象是否被凍結(jié)
  • isExtensible,判斷對象是否可以被擴展
  • keys,返回一個由給定對象的所有可以枚舉自身屬性的屬性名組成的數(shù)組

3.Array

  • Array.isArray,確定某個值到底是不是數(shù)組,不管它在哪個全局執(zhí)行環(huán)境中創(chuàng)建
  • push,接收任意數(shù)量的參數(shù),把它們逐個添加到數(shù)組末尾,并返回修改后數(shù)組的長度
  • pop,在數(shù)組尾部移除最后一項,減少數(shù)組的 length 值,然后返回移除的項
  • shift,移除數(shù)組中的第一項并返回該項,同時將數(shù)組長度減 1
  • unshift,在數(shù)組前端添加任意個項,并返回新數(shù)組的長度
  • reverse,反轉(zhuǎn)數(shù)組項的順序,返回排序后的數(shù)組
  • sort,默認情況下,按升序排序數(shù)組項,返回排序后的數(shù)組
  • concat,創(chuàng)建當前數(shù)組的一個副本,將接收到的參數(shù)添加到這個副本的末尾,返回新構(gòu)建的數(shù)組
  • join,用指定的字符拼接數(shù)組,返回拼接好的字符串
  • slice,基于當前數(shù)組中的一個或多個創(chuàng)建一個新數(shù)組,不影響原始數(shù)組
  • splice,根據(jù)傳入?yún)?shù)不同,可以刪除、插入、替換數(shù)組元素,返回一個數(shù)組,該數(shù)組中包含從原始數(shù)組中刪除的項,如果沒有刪除任何項,則返回空數(shù)組
  • indexOf,返回根據(jù)給定元素找到的第一個索引值,如果不存在則返回 -1
  • lastIndexOf,返回指定元素在數(shù)組中的最后一個索引值,如果不存在則返回 -1
  • every ,對數(shù)組中的每一項運行給定函數(shù) ,如果該函數(shù)對每一項都返回 true,則返回 true
  • filter,對數(shù)組中的每一項運行給定函數(shù) ,返回該函數(shù)會返回 true 的項組成的數(shù)組
  • forEach,對數(shù)組中的每一項運行給定函數(shù),沒有返回值
  • map,對數(shù)組中的每一項運行給定函數(shù),返回每次函數(shù)調(diào)用的結(jié)果組成的數(shù)組
  • some,對數(shù)組中的每一項運行給定函數(shù),如果函數(shù)對任一項返回 true,則返回 truereduce,接收一個函數(shù)作為累加器,數(shù)組中的每個值(從左到右)開始縮減,最終縮減為一個值
  • reduceRight,接收一個函數(shù)作為累加器,數(shù)組中的每個值(從右到左)開始縮減,最終縮減為一個值

4.String

  • charAt,訪問字符串中特定字符,返回給定位置的字符
  • charCodeAt,訪問字符串中特定字符,返回給定位置的字符的字符編碼
  • concat,將一個或多個字符串拼接起來,返回拼接得到的新字符串
  • match,查找匹配的字符串,返回一個數(shù)組
  • search,查找匹配的字符串,返回匹配項的索引,沒有找到,返回 -1
  • replace,替換字符串
  • split,基于指定的分隔符將一個字符串分割成多個字符串,將結(jié)果放在一個數(shù)組中,并返回
  • trim,創(chuàng)建一個字符串的副本,刪除前置及后綴的所有空格,然后返回結(jié)果
  • localeCompare,比較兩個字符串
  • slice,返回被操作字符串的一個子字符串
  • substr,返回被操作字符串的一個子字符串
  • substring,返回被操作字符串的一個子字符串

注意:slice、substr、substring 都接受一個或兩個參數(shù),第一個參數(shù)指定字符串的開始位置,第二個參數(shù)表示子字符串到哪里結(jié)束,slice 和 substring 的第二個參數(shù)指定的是子字符串的最后一個字符后面的位置,substr 第二個參數(shù)指定的是返回的字符個數(shù),如果沒有傳遞第二個參數(shù),則將字符串的末尾作為結(jié)束位置。

5.Function

  • arguments.callee,該屬性是一個指針,指向擁有這個 arguments 對象的函數(shù)
  • arguments.caller,該屬性保存著調(diào)用當前函數(shù)的函數(shù)的引用
  • apply,在特定的作用域中調(diào)用函數(shù),第一個參數(shù)是在其中運行函數(shù)的作用域,第二個是參數(shù)數(shù)組
  • call,在特定的作用域中調(diào)用函數(shù),第一個參數(shù)是在其中運行函數(shù)的作用域,其余參數(shù)直接傳遞給函數(shù)
  • bind,創(chuàng)建一個函數(shù)的實例,其 this 值會被綁定到傳給 bind 函數(shù)的值

6.JSON

  • JSON.parse,解析字符串為 JSON 對象
  • JSON.stringify,解析 JSON 對象為字符串
  • JSON.valueOf,獲取某個JSON 對象中的值
  • JSON.toString,被調(diào)用時,會調(diào)用 Object 原型上的 toString 方法,會獲的 JSON 對象的值并轉(zhuǎn)為字符串,如果沒有具體的值,則返回原型數(shù)組
  • JSON.toLocaleString,也是Object 原型上的方法,經(jīng)常會返回與 toString 相同內(nèi)容,但是對于 Date 對象,則會返回格式化的時間字符串

7.其他

  • Date.now,返回當前時間戳
  • Date.toJSON,將 Date 對象轉(zhuǎn)換為字符串,格式為 JSON 日期
  • Math.min,確定一組數(shù)值中的最小值
  • Math.max,確定一組數(shù)值中的最大值
  • Math.random,返回大于 0 小于 1 的一個隨機數(shù)
  • Number.prototype.toFixed,按照指定的小數(shù)位返回數(shù)值的字符串表示

ES6(2015)

1. 類(class)

class Man {
  constructor(name) {
    this.name = '你好世界';
  }
  console() {
    console.log(this.name);
  }
}
const man = new Man('你好世界');
man.console(); // 你好世界

2. 模塊化(ES Module)

// 模塊 A 導出一個方法
export const sub = (a, b) => a + b;
// 模塊 B 導入使用
import { sub } from './A';
console.log(sub(1, 2)); // 3

3. 箭頭(Arrow)函數(shù)

const func = (a, b) => a + b;
func(1, 2); // 3

4. 函數(shù)參數(shù)默認值

function foo(age = 25,){ // ...}

5. 模板字符串

const name = '你好世界';
const str = `Your name is ${name}`;

6. 解構(gòu)賦值

let a = 1, b= 2;
[a, b] = [b, a]; // a 2  b 1

7. 延展操作符

let a = [...'hello world']; // ["h", "e", "l", "l", "o", " ", "w", "o", "r", "l", "d"]

8. 對象屬性簡寫

const name='你好世界',
const obj = { name };

9. Promise

Promise 代表一個異步操作的執(zhí)行返回狀態(tài),這個執(zhí)行返回狀態(tài)在 Promise 對象創(chuàng)建時是未知的,它允許為異步操作的成功或失敗指定處理方法。

9.1 Promise 的狀態(tài)有三種

  • Fulfilled,表示 Promise 執(zhí)行成功
  • Rejected,表示 Promise 執(zhí)行失敗
  • Pending,表示 Promise 正在執(zhí)行中

9.2 Promise 對象有兩個特點

  • 對象的狀態(tài)不受外界影響
  • 一旦狀態(tài)改變就不會再變,任何時候都可以得到這個結(jié)果

9.3 缺點

  • 無法取消 Promise,一旦新建它就會立即執(zhí)行,無法中途取消
  • 如果不設(shè)置回調(diào)函數(shù),Promise 內(nèi)部拋出的錯誤不會反應(yīng)到外部
  • 當處于 Pending 狀態(tài)時,無法得知目前進展到哪一個階段(剛開始還是即將完成)

9.4 基本用法

var promise = new Promise(function(resolve, reject) {
    // ... some code

    if ( /*異步操作成功*/ ) {
        resolve(value)
    } else {
        reject(error)
    }
})

promise.then(function(value) {
    // success
}, function(error) {
    // failure
})

9.5 Promise 實例方法

  • Promise.prototype.then(),為 Promise 實例添加狀態(tài)改變時的回調(diào)函數(shù),返回一個新的 Promise 實例
  • Promise.prototype.catch(),用于指定發(fā)生錯誤時的回調(diào)函數(shù),返回一個新的 Promise 實例
  • Promise.prototype.done(),總是處于回調(diào)鏈的尾端,保證捕捉到任何可能出現(xiàn)的錯誤
  • Promise.prototype.finally(),用于指定不管 Promise 對象最后狀態(tài)如何都會執(zhí)行的操作。

finally 與 done 的最大區(qū)別在于:finally 接受一個普通的回調(diào)函數(shù)作為參數(shù),該函數(shù)不管怎樣都必須執(zhí)行。

9.6 Promise 對象方法

  • Promise.all(),將多個 Promise 實例包裝成一個新的 Promise 實例。
var p = Promise.all([p1, p2, p3])

p 的狀態(tài)由 p1,p2,p3 決定:

第一,只有 p1,p2,p3 的狀態(tài)都編程 Fulfilled,p 的狀態(tài)才會變成 Fulfilled,此時p1,p2,p3 的返回值組成一個數(shù)組,傳遞給 p 的回調(diào)函數(shù)。

第二,只要 p1,p2,p3 中有一個被 Rejected,p 的狀態(tài)就變成 Rejected,此時第一個被 Rejected 的實例的返回值會傳遞給 p 的回調(diào)函數(shù)

  • Promise.race(),將多個 Promise 實例包裝成一個新的 Promise 實例。
var p = Promise.race([p1, p2, p3])

只要 p1,p2,p3 中有一個實例率先改變狀態(tài),p 的狀態(tài)就跟著改變,那個率先改變的 Promise 實例的返回值就傳遞給 p 的回調(diào)函數(shù)。

  • Promise.resolve(),將現(xiàn)有對象轉(zhuǎn)為 Promise 對象,狀態(tài)為 Resolved
  • Promise.reject(),將現(xiàn)有對象轉(zhuǎn)為 Promise 對象,狀態(tài)為 Rejected
Promise.resolve().then(() => { console.log(2); });
console.log(1);
// 先打印 1 ,再打印 2

10. let和const

let name = '你好世界';
const arr = [];

11. 數(shù)組的新特性

ES6 為數(shù)組內(nèi)置對象添加了較多的新特性,主要包括 ... 復制數(shù)組和新增的數(shù)組 API。

const arr = [1, 2, 3]
const newArr = [...arr]  //[1, 2, 3]

注意:這里 ... 進行的數(shù)組復制是淺拷貝。

ES6 數(shù)組的新增方法:

  • Array.from,用于將類數(shù)組對象(包括 [array-like object] 和可遍歷對象)轉(zhuǎn)化為真正的數(shù)組
  • Array.of,可以將傳入的一組參數(shù)值轉(zhuǎn)換為數(shù)組
  • Array.prototype.copyWithin,可以在當前數(shù)組內(nèi)部將指定位置的數(shù)組項復制到其他位置,然后返回當前數(shù)組,使用 copyWithin 方法會修改當前數(shù)組
  • Array.prototype.fill,使用給定值,填充一個數(shù)組,會改變原來的數(shù)組
  • Array.prototype.find,用于找出第一個符合條件的數(shù)組元素,有點類似于 filter
  • Array.prototype.findIndex,用來返回某個特定數(shù)組元素在數(shù)組中的位置
  • Array.prototype.entries,對數(shù)組中鍵值對進行遍歷
  • Array.prototype.keys,對數(shù)組鍵名進行遍歷
  • Array.prototype.values,對數(shù)組鍵值進行遍歷
  • for...of 循環(huán)進行遍歷
  • Array.prototype[Symbol.iterator],用來獲取遍歷數(shù)組對象的迭代器

11. 函數(shù)參數(shù)

ES6 對函數(shù)參數(shù)進行了新的設(shè)計,主要添加了默認參數(shù)、不定參數(shù)和擴展參數(shù):

// 默認參數(shù)
function sayHi(name = 'zhangsan') {
    console.log(`Hello ${name}`)
}
sayHi() // Hello zhangsan


// 不定參數(shù)
function sayHi(...name) {
    console.log(name.reduce((a, b) => `Hello ${a} $`))
}
sayHi('zhangsan', 'lisi') 


// 擴展參數(shù)
let name = ['zhangsan', 'lisi']
function sayHi(name1, name2) {
    console.log(`Hello ${name1} ${name2}`)
}
sayHi(...name) 

不定參數(shù)和擴展參數(shù)可以認為恰好是相反的兩個模式,不定參數(shù)是使用數(shù)組來表示多個參數(shù),擴展參數(shù)則是將多個參數(shù)映射到一個數(shù)組。

需要注意:不定參數(shù)的 ... 和數(shù)組復制的 ... 是有區(qū)別的,不定參數(shù)可以使用函數(shù)的形參來表示所有的參數(shù)組成的列表。以前的 arguments 變量也有類似的作用,但是 arguments 不是真正的數(shù)組,除了存放參數(shù)的列表外,arguments 還有 length 屬性,嚴格來說 arguments 是一個類數(shù)組對象,而不定參數(shù)則是一個完全的數(shù)組,這也是不定參數(shù)相對于 arguments 的優(yōu)勢,更加方便我們使用,所以建議使用不定參數(shù)來代替 arguments。

12. 集合類型 Map + Set + WeakMap + WeakSet

12.1 Set

Set 本身是一個構(gòu)造函數(shù) ,用來生成 Set 數(shù)據(jù)結(jié)構(gòu),Set 類似于數(shù)組(但它不是數(shù)組),Set 的成員的值都是唯一的,沒有重復的值,也常用它來去重(不可以傳遞對象)。像 Set 加入值的時候,不會發(fā)生類型轉(zhuǎn)換,所以 5 和 “5” 是兩個不同的值。

const arr = new Set([1, 2, 3, 4, 5, 5, 5, 5])

console.log(arr)  //[1, 2, 3, 4, 5]
console.log(arr.size)  //5 

操作方法:

  • add(value),添加某個值,返回 Set 結(jié)構(gòu)本身
  • delete value,刪除某個值,返回一個布爾值,表示刪除是否成功
  • has(value),返回一個布爾值,表示該值是否為 Set 成員
  • clear(),清除所有成員,沒有返回值

遍歷方法:

  • keys(),返回鍵名的遍歷器
  • values(),返回鍵值的遍歷器
  • entries(),返回鍵值對的遍歷器
  • forEach(),使用回調(diào)函數(shù)遍歷每個成員

12.2 WeakSet

WeakSet 結(jié)構(gòu)與 Set 類似,也是不重復的值的集合,但是,它與 Set 有兩個區(qū)別:

第一,WeakSet 的成員只能是對象,而不能是其他類型的值。

第二,WeakSet 中的對象都是弱引用,即垃圾回收機制 不考慮 WeakSet 對該對象的引用,也就是說,如果其他對象都不在引用該對象,那么垃圾回收機制會自動回收該對象所占用的內(nèi)存,不考慮該對象是否還存在于 WeakSet 中。因此 ES6 規(guī)定 WeakSet 不可遍歷。

12.3 Map

傳統(tǒng)的 JavaScript 的對象(Object),本質(zhì)上是鍵值對的集合(Hash 結(jié)構(gòu)),但是只能用字符串當做鍵,這給它的使用帶來了很大的限制,而 ES6 提供了 Map 數(shù)據(jù)結(jié)構(gòu),它類似于對象,也是鍵值對的集合,但是“鍵” 的范圍不限于字符串,各種類型的值(包括對象)都可以當做鍵。也就是說,Object 結(jié)構(gòu)提供了“字符串-值”的對應(yīng),Map 結(jié)構(gòu)提供了“值-值”的對應(yīng),是一種更完善的 Hash 結(jié)構(gòu)實現(xiàn)。Map 的鍵實際上是跟內(nèi)存地址綁定的,只要內(nèi)存地址不一樣,就視為兩個鍵。

操作方法:

  • set(key, value),設(shè)置 key 所對應(yīng)的鍵值,返回整個 Map 結(jié)構(gòu) ,如果 key 已經(jīng)有值,則鍵值會被更新,否則就生成該鍵
  • get(key),讀取 key 對應(yīng)的鍵值,如果在好不到 key,則返回 undefined
  • has(key),返回一個 布爾值,表示某個鍵是否在 Map 數(shù)據(jù)結(jié)構(gòu)中
  • delete(key),刪除某個鍵,返回 true,如果刪除失敗,則返回 false
  • clear(),清除所有成員,沒有返回值

遍歷方法:

  • keys(),返回鍵名的遍歷器
  • values(),返回鍵值的遍歷器
  • entries(),返回所有成員的遍歷器
  • forEach(),遍歷 Map 的所有成員

12.4 WeakMap

WeakMap 結(jié)構(gòu)與 Map 結(jié)構(gòu)類似,也用于生成鍵值對的集合,但 WeakMap 與 Map 有兩個個區(qū)別:

第一,WeakMap 只接受對象作為鍵名(null 除外),不接受其他類型的值作為鍵名。

第二,WeakMap 的鍵名所指向的對象不計入垃圾回收機制。它的鍵名所引用的對象都是弱引用,即垃圾回收機制不將該引用考慮在內(nèi),因此,只要所引用的對象的其他引用被清除了,垃圾回收機制就會釋放該對象所占用的內(nèi)存。也就是說, 一旦不再需要,WeakMap 里面的鍵名對象和所對應(yīng)的鍵值對會自動消失,不用手動刪除引用?;旧希绻雽ο笾刑砑訑?shù)據(jù)又不想干擾垃圾回收機制,便可以使用 WeakMap。一個典型的應(yīng)用場景是,在網(wǎng)頁的 DOM 元素上添加數(shù)據(jù)時就可以使用 WeakMap 結(jié)構(gòu),當該 DOM 元素被清除,其對應(yīng)的 WeakMap 記錄就會自動被移除。

注意:WeakMap 的專用場景就是它的鍵所對應(yīng)的對象可能會在將來消失,WeakMap 結(jié)構(gòu)有助于防止內(nèi)存泄露。但是,WeakMap 弱引用的只是鍵名而不是鍵值,鍵值依然是正常引用的。

13. Symbol 類型

ES6 引入了一種新的原始數(shù)據(jù)類型 Symbol,表示獨一無二的值,它是 JavaScript 語言的第 7 種數(shù)據(jù)類型,前 6 種分別是:Undefined、Null、Boolean、String、Number 和 Object。

Symbol 值通過 Symbol 函數(shù)生成,一般作為屬性鍵值,并且能避免對象屬性鍵的命名沖突。也就是說,對象的屬性名現(xiàn)在可以有兩種類型:一種是原來就有的字符串,另一種就是新增的 Symbol 類型。只要屬性名屬于 Symbol 類型,就是獨一無二的,可以保證不會與其他屬性名產(chǎn)生沖突。

let s = Symbol('foo')

typeof s  //"symbol"

注意:

Symbol 函數(shù)前不能使用 new 命令,否則會報錯,這是因為生產(chǎn)的 Symbol 是一個原始類型的值,不是對象。也就是說,由于 Symbol 值不是對象,所以不能添加屬性。基本上,它是一種類似于字符串的數(shù)據(jù)類型。

Symbol 函數(shù)的參數(shù)只表示對當前 Symbol 值的描述,因此相同參數(shù)的 Symbol 函數(shù)的返回值是不相等的。

Symbol 值作為對象屬性名時不能使用點運算符:

let s = Symbol()

let obj = {
    [s]: function() {
        console.log('Hello')
    }
}

obj[s]()  // 'Hello'

Symbol 做為屬性名,該屬性不會出現(xiàn)在 for...in,for...of 循環(huán)中,也不會被 Object.keys()、Object.getOwnpropertyNames() 返回,但它也不是私有屬性,Object.getOwnPropertySymbols() 可以獲取指定對象的所有 Symbol 屬性名。 Object.getOwnPropertySymbols() 返回一個數(shù)組,成員是當前對象的所有用作屬性名的 Symbol 值。

Proxy

Proxy 用于修改某些操作的默認行為,可以用來攔截某個對象的屬性訪問方法,然后重載對象的 “ . ” 運算符。

Proxy 可以理解成在目標對象前架設(shè)一個“攔截”層,外界對該對象的訪問都必須先通過這層攔截,因此提供了一種機制可以對外界的訪問進行過濾和改寫。

let object = new Proxy({}, {
    get: function(target, key, receiver) {
        console.log(`getting ${key}`)
        return Reflect.get(target, key, receiver)
    },
    set: function(target, key, value, receiver) {
        console.log(`setting ${key}`)
        return Reflect.set(target, key, value, receiver)
    }
})

對比 Object.defineProperty 方法:

let object = {},
    value

Object.defineProperty(object, 'value', {
    get: function() {
        console.log('getting value')
        return value
    },
    set: function(newValue) {
        value = newValue
        console.log('setting: ' + newValue)
    },
    enumerable: true,
    configurable: true
})

Reflect

Reflect 對象的設(shè)計目的有以下幾個:

第一,將 Object 對象的一些明顯屬于語言內(nèi)部的方法(如 Object.defineProperty)放到 Reflect 對象上,現(xiàn)階段,某些方法同時在 Object 和 Reflect 對象上部署,未來新的方法只在 Reflect 對象上部署。也就是說,從 Reflect 對象上可以獲得語言內(nèi)部的方法。

第二,修改某些 Object 方法的返回結(jié)果,讓其變得更加合理。

第三,讓 Object 操作都編程函數(shù)行為,某些 Object 操作是命令式,比如 name in obj 和 delete obj [name],而 Reflect.has(obj, name) 和 Reflect.deleteProperty(obj, name) 讓它們變成了函數(shù)行為。

第四,Reflect 對象的方法與 Proxy 對象的方法一一對應(yīng),只要是 Proxy 對象的方法,就能在 Reflect 對象上找到對應(yīng)的方法,這就是 Proxy 對象可以方便的調(diào)用對應(yīng)的 Reflect 方法來完成默認行為,作為修改行為的基礎(chǔ)。也就是說,無論 Proxy 怎么修改默認行為,我們總可以在 Reflect 上獲取到默認行為。

Iterator

Iterator即迭代器,它是一種接口,為各種不同的數(shù)據(jù)結(jié)構(gòu)提供了統(tǒng)一的訪問機制,換句話說,只要有任何數(shù)據(jù)結(jié)構(gòu)部署了迭代接口,就可以使用統(tǒng)一的方式的來遍歷它。

實現(xiàn)可迭代接口的數(shù)據(jù)結(jié)構(gòu),一般都自身實現(xiàn)或繼承了以Symbol.iterator屬性的,就屬于可迭代對象。Symbol.iterator屬性本身是一個函數(shù),就是當前數(shù)據(jù)結(jié)構(gòu)默認的遍歷器生成函數(shù)。

一個包含next()方法的對象,才可以稱為一個迭代對象。next()對象的會有返回一個對象,對象中包含兩個值,如下所示:

  • value:迭代器返回的任何JavaScript值。donetrue時可省略。
  • done:一個布爾值,為false時表示迭代未停止,為true時立即停止迭代器,且可以省略value的值。

JavaScript原生提供的迭代器接口如下圖所示:

Generator

Generator是ES2015中提供的一種異步編程解決方案,定義Generator函數(shù)在function關(guān)鍵字和函數(shù)名中間使用*星號,函數(shù)內(nèi)部使用yield關(guān)鍵字定義不同的狀態(tài)。

示例代碼如下:

function* testGenerator() {
  // yield定義一個狀態(tài)
  yield '一碗周'
  yield 'es新特性'
  return 'generator' // 終結(jié)Generator,后面即使有yield關(guān)鍵字也無效
}
const g = testGenerator() // 返回 Generator 對象,通過next()方法移動狀態(tài)

g.next()
/* { value: '一碗周', done: false } */

g.next()
/* { value: 'es新特性', done: false } */

g.next()
/* { value: 'generator', done: true } */

ES7(2016)

1. 冪指數(shù)操作符

增加了冪指數(shù)操作符來進行冪指數(shù)運算:

console.log(2 ** 3)  // 8

x ** y 產(chǎn)生的結(jié)果等同于 Math.pow(x, y)

2. Array.prototype.includes

這個數(shù)組方法主要用來判斷數(shù)組中是否包含某個元素:

let num = [1, 2, 3, 4, 5]

console.log(num.includes(1))  // true

ES8(2017)

1. 異步函數(shù) async/await

async 函數(shù)返回一個 Promise 對象,可以使用 then 方法添加回調(diào)函數(shù)。當函數(shù)執(zhí)行的時候,一旦遇到 await 就會先返回,等到異步操作完成,再接著執(zhí)行函數(shù)體內(nèi)后面的語句。

function timeout(ms) {
    return new Promise(resolve => {
        setTimeout(resolve, ms)
    })
}

async function asyncPrint(value, ms) {
    await timeout(ms)
    console.log(value)
}

asyncPrint('Hello', 300)

上訴代碼指定 300ms 后輸出 Hello。

async 函數(shù)返回一個 Promise 對象,async 函數(shù)內(nèi)部 return 語句返回的值,會成為 then 方法回調(diào)函數(shù)的參數(shù):

async function f() {
    return 'Hello'
}

f().then(v => console.log(v))  // 'Hello'

async 函數(shù)內(nèi)部拋出錯誤會導致返回的 Promise 對象變成 rejected 狀態(tài),拋出的錯誤對象會被 catch 方法回調(diào)函數(shù)接受到:

async function f() {
    throw new Error('出錯了')
}

f().then(
    v => console.log(v),
    e => console.log(e)
)   // ‘Error: 出錯了'

正常情況下,await 命令后面是一個 Promise 對象,如果不是,會被轉(zhuǎn)為一個立即 resolve 的 Promise 對象。

await 命令后面的 Promise 對象如果變成 rejected 狀態(tài),則 reject 的參數(shù)會被 catch 方法的回調(diào)函數(shù)接收到。

只要一個 await 語句后面的 Promise 變成 rejected,那么整個 async 函數(shù)都會被中斷執(zhí)行。

注意:

  • await 命令后面的 Promise 對象的運行結(jié)果可能是 rejected,最好把 await 命令放在 try...catch 中。
  • 多個 await 命令后面的異步操作如果不存在繼發(fā)關(guān)系,最好讓它們同時觸發(fā)。
  • await 命令只能用在 async 函數(shù)中,如果用在普通函數(shù)中就會報錯。

2. Object.values()

Object.values({a: 1, b: 2, c: 3}); // [1, 2, 3]

3. Object.entries()

Object.entries({a: 1, b: 2, c: 3}); // [["a", 1], ["b", 2], ["c", 3]]

4. Object.getOwnPropertyDescriptors()

5. String padding

// padStart
'hello'.padStart(10); // "     hello"
// padEnd
'hello'.padEnd(10) "hello     "

6. 函數(shù)參數(shù)列表結(jié)尾允許逗號

7. Object.getOwnPropertyDescriptors()

獲取一個對象的所有自身屬性的描述符,如果沒有任何自身屬性,則返回空對象。

8. SharedArrayBuffer對象

SharedArrayBuffer 對象用來表示一個通用的,固定長度的原始二進制數(shù)據(jù)緩沖區(qū),
/**
 * 
 * @param {*} length 所創(chuàng)建的數(shù)組緩沖區(qū)的大小,以字節(jié)(byte)為單位。  
 * @returns {SharedArrayBuffer} 一個大小指定的新 SharedArrayBuffer 對象。其內(nèi)容被初始化為 0。
 */
new SharedArrayBuffer(10)

9. Atomics對象

Atomics 對象提供了一組靜態(tài)方法用來對 SharedArrayBuffer 對象進行原子操作。

ES9(2018)

1. 異步迭代

await可以和for...of循環(huán)一起使用,以串行的方式運行異步操作

async function process(array) {
  for await (let i of array) {
    // doSomething(i);
  }
}

2. Promise.finally()

Promise.resolve().then().catch(e => e).finally();

3. Rest/Spread 屬性

const values = [1, 2, 3, 5, 6];
console.log( Math.max(...values) ); // 6

4. 正則表達式命名捕獲組

const reg = /(?<year>[0-9]{4})-(?<month>[0-9]{2})-(?<day>[0-9]{2})/;
const match = reg.exec('2021-02-23');

5. 正則表達式反向斷言

(?=p)、(?<=p)  p 前面(位置)、p 后面(位置)
(?!p)、(?<!p>) 除了 p 前面(位置)、除了 p 后面(位置)

(?<=w)

(?<!w)

6. 正則表達式dotAll模式

正則表達式中點.匹配除回車外的任何單字符,標記s改變這種行為,允許行終止符的出現(xiàn)
/hello.world/.test('hello\nworld');  // false

ES10(2019)

1. Array.flat()和Array.flatMap()

flat()

[1, 2, [3, 4]].flat(Infinity); // [1, 2, 3, 4]

flatMap()

[1, 2, 3, 4].flatMap(a => [a**2]); // [1, 4, 9, 16]

2. String.trimStart()和String.trimEnd()

去除字符串首尾空白字符

3. String.prototype.matchAll

matchAll()為所有匹配的匹配對象返回一個迭代器
const raw_arr = 'test1  test2  test3'.matchAll((/t(e)(st(\d?))/g));
const arr = [...raw_arr];

4. Symbol.prototype.description

只讀屬性,回 Symbol 對象的可選描述的字符串。
Symbol('description').description; // 'description'

5. Object.fromEntries()

返回一個給定對象自身可枚舉屬性的鍵值對數(shù)組
// 通過 Object.fromEntries, 可以將 Map 轉(zhuǎn)化為 Object:
const map = new Map([ ['foo', 'bar'], ['baz', 42] ]);
console.log(Object.fromEntries(map)); // { foo: "bar", baz: 42 }

6. 可選 Catch

ES11(2020)

1. Nullish coalescing Operator(空值處理)

表達式在 ?? 的左側(cè) 運算符求值為undefined或null,返回其右側(cè)。

let user = {
    u1: 0,
    u2: false,
    u3: null,
    u4: undefined
    u5: '',
}
let u2 = user.u2 ?? '用戶2'  // false
let u3 = user.u3 ?? '用戶3'  // 用戶3
let u4 = user.u4 ?? '用戶4'  // 用戶4
let u5 = user.u5 ?? '用戶5'  // ''

2. Optional chaining(可選鏈)

?.用戶檢測不確定的中間節(jié)點

let user = {}
let u1 = user.childer.name // TypeError: Cannot read property 'name' of undefined
let u1 = user.childer?.name // undefined

3. Promise.allSettled

返回一個在所有給定的promise已被決議或被拒絕后決議的promise,并帶有一個對象數(shù)組,每個對象表示對應(yīng)的promise結(jié)果
const promise1 = Promise.resolve(3);
const promise2 = 42;
const promise3 = new Promise((resolve, reject) => reject('我是失敗的Promise_1'));
const promise4 = new Promise((resolve, reject) => reject('我是失敗的Promise_2'));
const promiseList = [promise1,promise2,promise3, promise4]
Promise.allSettled(promiseList)
.then(values=>{
  console.log(values)
});

4. import()

按需導入

5. 新基本數(shù)據(jù)類型BigInt

任意精度的整數(shù)

6. globalThis

  • 瀏覽器:window
  • worker:self
  • node:global

ES12(2021)

1. replaceAll

返回一個全新的字符串,所有符合匹配規(guī)則的字符都將被替換掉
const str = 'hello world';
str.replaceAll('l', ''); // "heo word"

2. Promise.any

Promise.any() 接收一個Promise可迭代對象,只要其中的一個 promise 成功,就返回那個已經(jīng)成功的 promise 。如果可迭代對象中沒有一個 promise 成功(即所有的 promises 都失敗/拒絕),就返回一個失敗的 promise
const promise1 = new Promise((resolve, reject) => reject('我是失敗的Promise_1'));
const promise2 = new Promise((resolve, reject) => reject('我是失敗的Promise_2'));
const promiseList = [promise1, promise2];
Promise.any(promiseList)
.then(values=>{
  console.log(values);
})
.catch(e=>{
  console.log(e);
});

3. WeakRefs

使用WeakRefs的Class類創(chuàng)建對對象的弱引用(對對象的弱引用是指當該對象應(yīng)該被GC回收時不會阻止GC的回收行為)

4. 邏輯運算符和賦值表達式

邏輯運算符和賦值表達式,新特性結(jié)合了邏輯運算符(&&,||,??)和賦值表達式而JavaScript已存在的 復合賦值運算符有:
a ||= b
//等價于
a = a || (a = b)

a &&= b
//等價于
a = a && (a = b)

a ??= b
//等價于
a = a ?? (a = b)

5. 數(shù)字分隔符

數(shù)字分隔符,可以在數(shù)字之間創(chuàng)建可視化分隔符,通過_下劃線來分割數(shù)字,使數(shù)字更具可讀性
const money = 1_000_000_000;
//等價于
const money = 1000000000;

1_000_000_000 === 1000000000; // true

ES13(2022)

1.class的擴展

在ES2022中允許我們并不在constructor中定義類的成員,示例代碼如下:

class C {
  myName = '一碗周'
}
/* 兩者是一致的 */
class C {
  constructor() {
    myName = '一碗周'
  }
}
如果成員只聲明不初始化它的默認值是undefined。

在ES2022中允許我們使用#開頭命名的變量作為類的私有成員,示例代碼如下:

class C {
  #myName = '一碗周'
}
const c = new C()
console.log(#myName) //  Private field '#myName' must be declared in an enclosing class

2. await在頂層使用

在ES2022中新增了允許在頂層使用await,在頂層可以不適用async函數(shù)進行包裹,示例代碼如下:

import { AsyncFun } from 'module'
await AsyncFun()
console.log(123)

3. Object.hasOwn()

Object.hasOwn()方法用于判斷某個對象上是否具有某個屬性,示例代碼如下:

const person = {
  name: '一碗周',
  age: 18,
}
console.log(Object.hasOwn(person, 'name')) // true
console.log(Object.hasOwn(person, 'sex')) // false

4. Array.prototype.at()

ES2022中新增的at()方法,它的作用是獲取數(shù)組中的某個成員,它的參數(shù)是數(shù)組的索引,與直接使用索引的方式不同,它允許我們傳遞負值,等同于從后面倒數(shù),示例代碼如下:

const arr = [1, 2, 3, 4, 5, 6]
console.log(arr.at(-1)) // 6
// 等同于 arr[arr.length - 1]

5. d修飾符

正則表達式增加了一個/d修飾符,當使用正則表達式的exec()方法時,如果有/d修飾符,那么結(jié)果會多返回一個indices屬性,用來表示匹配的結(jié)果的在原字符串中的起始index值。示例代碼如下:

const str = 'JavaScript'
const r = /a/d

const m = r.exec(str)
console.log(m.indices[0]) //[ 1, 2 ]

6. 頂層 await

之前await關(guān)鍵字只能在async函數(shù)內(nèi)部使用,在外部使用就會報錯: SyntaxError - SyntaxError: await is only valid in async function;

在ES13 允許在模塊的頂層使用 await, 并且不再需要配合 async函數(shù)使用,它允許模塊充當大型異步函數(shù),使得我們在 ESM 模塊中可以等待資源的加載,只有資源加載完畢之后才會去執(zhí)行當前模塊的代碼。

實際運用:

a、動態(tài)加載模塊

const strings = await import(`/i18n/${navigator.language}`);

這對于開發(fā)/生產(chǎn)拆分、國際化、環(huán)境拆分等非常有用。

b、資源初始化

const connection = await dbConnector();

配合try catch實現(xiàn)依賴回退

let jQuery;
try {
  jQuery = await import('https://cdn-a.com/jQuery');
} catch {
  jQuery = await import('https://cdn-b.com/jQuery');
}

依賴發(fā)生故障時,可以回退到舊版本,防止程序崩潰。

7. at()

.at()是數(shù)組新增的一個方法,通過傳遞給定索引來獲取數(shù)組元素,這個索引可以是正數(shù)也可以是負數(shù),當索引是正數(shù)時效果和 [] 是一樣的,當索引是負數(shù)時就會從數(shù)組的最后一項開始。

const arr = [1,2,3,4,5]; 
arr[arr.length-1] // 5
const arr = [1,2,3,4,5]; 
arr.at(-1) // 5

支持類型

  • String
  • Array
  • Typed Array

ES14(2023)

1. Array.prototype.toSorted

toSorted() 與 Array.prototype.sort() 具有相同的簽名,但它創(chuàng)建一個新的數(shù)組,而不是對原數(shù)組進行操作。

let arr = [5, 4, 2, 3, 1];
arr === arr.sort(); // true - [1, 2, 3, 4, 5]

arr === arr.toSorted(); // false - [1, 2, 3, 4, 5]

toSorted() 和 sort() 一樣,接受一個可選參數(shù)作為比較函數(shù)。例如,我們可以使用 toSorted() 創(chuàng)建一個按降序排列的新數(shù)組

const numbers = [10, 5, 2, 7, 3, 9, 1, 6, 4];
const sortedNumbers = numbers.toSorted((a, b) => {
  return b - a;
});
console.log(sortedNumbers); // [10, 9, 8, 7, 6, 5, 4, 3, 2, 1]

需要注意的是,toSorted() 也可以應(yīng)用于對象數(shù)組。這種情況下,需要提供一個使用對象上的數(shù)據(jù)的比較函數(shù),因為對象沒有自然的排序方式。

// 比較對象
const objects = [
  { name: "John", age: 30 },
  { name: "Jane", age: 25 },
  { name: "Bill", age: 40 },
  { name: "Mary", age: 20 }
];
const sortedObjects = objects.toSorted((a, b) => {
  return a.name.localeCompare(b.name);
});
console.log(sortedObjects);
// [{"name":"Bill","age":40},{"name":"Jane","age":25},{"name":"John","age":30},{"name":"Mary","age":20}]

2. Array.prototype.toReversed

與 toSorted() 和 sort() 一樣,toReversed() 是 reverse() 的復制版本。

["a", "b", "c", "d", "e"].toReversed(); // ['e', 'd', 'c', 'b', 'a']

3. Array.prototype.with

新的 with() 方法允許您基于索引修改單個元素,并返回一個新的數(shù)組。因此,如果您知道索引和新值,這個方法非常方便。需要注意的是with() 是 set() 的復制伴侶。

const arr4 = ["I", "am", "the", "Walrus"];

// 用 "Ape Man" 替換字符串 "Walrus"。
const newArr4 = arr4.with(3, "Ape Man");

console.log(newArr4);

4. Array.prototype.findLast

findLast() 方法允許您從數(shù)組中獲取匹配元素的最后一個實例。如果找不到匹配元素,則返回 undefined。下面代碼中提供了一個簡單的示例,我們從數(shù)組中獲取最后一個偶數(shù)。

const arr = [54, 34, 55, 75, 98, 77];

const lastEvenIndex = arr.findLast((element) => {
  return element % 2 === 0;
});

console.log(lastEvenIndex); // 98

findLast() 還支持傳遞一個 "thisArg" 來設(shè)置上下文。也就是說,第二個參數(shù)將告訴第一個參數(shù)函數(shù) this 關(guān)鍵字將引用什么。從下面代碼中看到這一點,我們使用一個自定義對象來找到可以被 5 整除的第一個元素。

const arr6 = [54, 34, 55, 75, 98, 77];
const myObject = { testCase: 5 };
const lastEvenIndex = arr5.findLast((element) => {
  return element % myObject.testCase === 0;
}, myObject);

console.log(lastEvenIndex); // 75

5.Array.prototype.findLastIndex

findLastIndex() 的工作方式與 findLast() 相同,只是它返回匹配元素的索引而不是元素本身。例如,下面例子展示如何找到最后一個可以被 6 整除的元素的索引。

代碼清單 8. 使用 findLastIndex() 找到元素的索引

const arr = [54, 34, 55, 75, 98, 77];
arr.findLastIndex(x => x % 6 === 0); // 0

6.Array.prototype.toSpliced

上面新增的所有方法也適用于 TypedArray,但 toSpliced() 這個新的數(shù)組方法只存在于 Array 中。toSpliced() 方法是 splice() 的復制版本,splice()是js中數(shù)組操作常用的方法;

假設(shè)我們有一個顏色數(shù)組,需要在中間插入一些新的顏色(粉紅色和青色)。這會創(chuàng)建一個新數(shù)組,而不是修改原始數(shù)組。

const arr = ["red", "orange", "yellow", "green", "blue", "purple"];
const newArr = arr.toSpliced(2, 1, "pink", "cyan");
console.log(newArr);
// ["red", "orange", "pink", "cyan", "green", "blue", "purple"]
console.log(newArr[3]);
// 'cyan'
console.log(arr[3]);
// 'green'

7.正式的 shebang 支持

Shebang 是舊式 Unix 術(shù)語,表示井號后跟一個感嘆號:#!(其中 "bang" 是感嘆號的俚語)。

#!/bin/bash

echo "Hello, world!"

您可以使用 ./hello.sh 直接運行上面代碼。

您也可以在 JavaScript 中執(zhí)行類似操作,如代碼清單 11 所示。

#!/usr/bin/env node

console.log("Hello, world!");

上面例子告訴操作系統(tǒng)使用 node 程序來運行此腳本。只需鍵入 ./hello.js 即可運行它。如果沒有 #!是無法運行的。

Shebang 支持是規(guī)范中已經(jīng)實現(xiàn)并在多種情境下非正式采用的特性之一。

8.Symbol 作為 WeakMap 的鍵

ES14中的最后一個新功能是Symbol 可以作為 WeakMap 的鍵使用。在這之前,WeakMap僅允許對象作為鍵值,新特性更容易創(chuàng)建和共享key。

var map = new WeakMap(); // 創(chuàng)建一個弱映射
function useSymbol(symbol){
    doSomethingWith(symbol);
    var called = map.get(symbol) || 0

上面的例子允許從外部調(diào)用者調(diào)用計數(shù)器,并在不再有引用時釋放映射條目。代碼本身無法知道何時不再需要引用,如果使用普通的 Map,將會導致內(nèi)存泄漏。這是因為即使在調(diào)用它的客戶端不再需要引用時,代碼仍然會保留對該引用的持有。在這種情況下使用 WeakMap,可以確保垃圾回收在不再存在對鍵符號的引用時刪除映射條目。

9. Record 和 Tuple 類型

const person = {
  name: "John Doe",
  age: 30,
  hobbies: ["coding", "reading", "playing guitar"]
};

這段代碼定義了一個名為 person 的 Record,其中包含三個元素:姓名、年齡和愛好。name 元素是一個字符串,age 元素是一個整數(shù),hobbies 元素是一個字符串數(shù)組。

以下是 ES14 之后的 ECMAScript 2023 中的元組示例:

const colors = ["red", "green", "blue", "purple"];

此代碼定義了一個名為顏色的元組,其中包含四個元素:紅色、綠色、藍色和紫色。元組的元素現(xiàn)在可以是任何類型的數(shù)據(jù)。

總結(jié)

到此這篇關(guān)于js版本ES6、ES7、ES8、ES9、ES10、ES11、ES12、ES13、ES14[2023]新特性的文章就介紹到這了,更多相關(guān)js版本ES6-ES14的新特性集合內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • JS簡單驗證上傳文件類型的方法

    JS簡單驗證上傳文件類型的方法

    這篇文章主要介紹了JS簡單驗證上傳文件類型的方法,涉及javascript文件遍歷及字符串截取、匹配等相關(guān)操作技巧,需要的朋友可以參考下
    2017-04-04
  • JS操作json對象key、value的常用方法分析

    JS操作json對象key、value的常用方法分析

    這篇文章主要介紹了JS操作json對象key、value的常用方法,結(jié)合實例形式分析了js操作json對象鍵值對遍歷及增刪的相關(guān)操作技巧,需要的朋友可以參考下
    2019-10-10
  • 在 JavaScript 中管理 Token 的最佳實踐記錄

    在 JavaScript 中管理 Token 的最佳實踐記錄

    文章介紹了在JavaScript中管理Token的最佳實踐,包括Token的作用、存儲方式、代碼實現(xiàn)和安全性考慮,通過示例代碼,展示了如何在不同環(huán)境中動態(tài)設(shè)置Token作用域,并提供了安全存儲和保護Token的方法
    2024-11-11
  • three.js實現(xiàn)圍繞某物體旋轉(zhuǎn)

    three.js實現(xiàn)圍繞某物體旋轉(zhuǎn)

    本篇文章主要介紹了three.js實現(xiàn)圍繞某物體旋轉(zhuǎn)的示例代碼。具有很好的參考價值,下面跟著小編一起來看下吧
    2017-01-01
  • js數(shù)組合并的8種方法(最全)

    js數(shù)組合并的8種方法(最全)

    在JavaScript中,有多種方法可以合并數(shù)組,本文主要介紹了8種方法,主要包括concat()、spread operator、push()、unshift()、splice()、Array.from()、Array.prototype.reduce()和ES6的Array.prototype.flat(),感興趣的可以了解一下
    2023-08-08
  • js將控件隱藏及display屬性的使用介紹

    js將控件隱藏及display屬性的使用介紹

    用JavaScript隱藏控件的方法有兩種,分別是通過設(shè)置控件的style的“display”和“visibility”屬性,下面詳細為大家介紹下具體的使用
    2013-12-12
  • 一文了解你不知道的JavaScript閉包篇

    一文了解你不知道的JavaScript閉包篇

    這篇文章主要為大家詳細介紹了一些你不知道的JavaScript閉包相關(guān)知識,文中的示例代碼講解詳細,對我們學習JavaScript有一定幫助,感興趣的可以跟隨小編一起學習一下
    2022-11-11
  • layui禁用側(cè)邊導航欄點擊事件的解決方法

    layui禁用側(cè)邊導航欄點擊事件的解決方法

    今天小編就為大家分享一篇layui禁用側(cè)邊導航欄點擊事件的解決方法,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2019-09-09
  • javascript內(nèi)置對象Date案例總結(jié)分析

    javascript內(nèi)置對象Date案例總結(jié)分析

    今天總結(jié)javascript內(nèi)置對象Date的使用,并且寫一個重要的網(wǎng)頁倒計時的核心算法案例,有需要的朋友可以借鑒參考下希望能夠有所幫助,祝大家多多進步
    2022-03-03
  • 基于MooTools的很有創(chuàng)意的滾動條時鐘動畫

    基于MooTools的很有創(chuàng)意的滾動條時鐘動畫

    一款很有創(chuàng)意的時鐘js動畫.是利用系統(tǒng)滾動條來構(gòu)成一個 時:分:秒 的盤. 再利用滾動條的長度變化做過渡動畫.
    2010-11-11

最新評論