欧美亚洲中文,在线国自产视频,欧洲一区在线观看视频,亚洲综合中文字幕在线观看

      1. <dfn id="rfwes"></dfn>
          <object id="rfwes"></object>
        1. 站長(zhǎng)資訊網(wǎng)
          最全最豐富的資訊網(wǎng)站

          你知道JavaScript中的可迭代對(duì)象與迭代器嗎

          迭代是訪問集合元素的一種方法;可以被迭代的對(duì)象稱為可迭代對(duì)象;迭代器是一個(gè)可以記住遍歷位置的對(duì)象,迭代器對(duì)象從集合的第一個(gè)元素開始訪問,直到所有元素被訪問結(jié)束,迭代器只能前進(jìn)不會(huì)后退。

          Lazy evaluation

          Lazy evaluation常被譯為“延遲計(jì)算”或“惰性計(jì)算”,指的是僅僅在真正需要執(zhí)行的時(shí)候才計(jì)算表達(dá)式的值。

          與惰性求值相反的是及早求值(eager evaluation)及早求值,也被稱為貪婪求值(greedy evaluation)或嚴(yán)格求值,是多數(shù)傳統(tǒng)編程語言的求值策略。

          充分利用惰性求值的特性帶來的好處主要體現(xiàn)在以下兩個(gè)方面:

          • 避免不必要的計(jì)算,帶來性能上的提升。

          • 節(jié)省空間,使得無限循環(huán)的數(shù)據(jù)結(jié)構(gòu)成為可能。

          迭代器

          ES6 中的迭代器使惰性求值和創(chuàng)建用戶定義的數(shù)據(jù)序列成為可能。迭代是一種遍歷數(shù)據(jù)的機(jī)制。 迭代器是用于遍歷數(shù)據(jù)結(jié)構(gòu)元素(稱為Iterable)的指針,用于產(chǎn)生值序列的指針。

          迭代器是一個(gè)可以被迭代的對(duì)象。它抽象了數(shù)據(jù)容器,使其行為類似于可迭代對(duì)象。

          迭代器在實(shí)例化時(shí)不計(jì)算每個(gè)項(xiàng)目的值,僅在請(qǐng)求時(shí)才生成下一個(gè)值。 這非常有用,特別是對(duì)于大型數(shù)據(jù)集或無限個(gè)元素的序列。

          可迭代對(duì)象

          可迭代對(duì)象是希望其元素可被公眾訪問的數(shù)據(jù)結(jié)構(gòu)。JS 中的很多對(duì)象都是可迭代的,它們可能不是很好的察覺,但是如果仔細(xì)檢查,就會(huì)發(fā)現(xiàn)迭代的特征:

          • new Map([iterable])

          • new WeakMap([iterable])

          • new Set([iterable])

          • new WeakSet([iterable])

          • Promise.all([iterable])

          • Promise.race([iterable])

          • Array.from([iterable])

          還有需要一個(gè)可迭代的對(duì)象,否則,它將拋出一個(gè)類型錯(cuò)誤,例如:

          • for … of

          • … (展開操作符)
            const [a, b, ..] = iterable (解構(gòu)賦值)

          • yield* (生成器)

          JavaScript中已有許多內(nèi)置的可迭代項(xiàng):

          String,Array,TypedArray,Map,Set。

          迭代協(xié)議

          迭代器和可迭對(duì)象遵循迭代協(xié)議。

          協(xié)議是一組接口,并規(guī)定了如何使用它們。

          迭代器遵循迭代器協(xié)議,可迭代遵循可迭代協(xié)議。

          可迭代的協(xié)議

          要使對(duì)象變得可迭代,它必須實(shí)現(xiàn)一個(gè)通過Symbol.iterator的迭代器方法,這個(gè)方法是迭代器的工廠。

          使用 TypeScript,可迭代協(xié)議如下所示:

          interface Iterable {   [Symbol.iterator]() : Iterator; }

          Symbol.iterator]()是無參數(shù)函數(shù)。 在可迭代對(duì)象上調(diào)用它,這意味著我們可以通過this來訪問可迭代對(duì)象,它可以是常規(guī)函數(shù)或生成器函數(shù)。

          迭代器協(xié)議

          迭代器協(xié)議定義了產(chǎn)生值序列的標(biāo)準(zhǔn)方法。

          為了使對(duì)象成為迭代器,它必須實(shí)現(xiàn)next()方法。 迭代器可以實(shí)現(xiàn)return()方法,我們將在本文后面討論這個(gè)問題。

          使用 TypeScript,迭代器協(xié)議如下所示:

          interface Iterator {     next() : IteratorResult;     return?(value?: any): IteratorResult; }

          IteratorResult 的定義如下:

          interface IteratorResult {     value?: any;     done: boolean; }
          • done通知消費(fèi)者迭代器是否已經(jīng)被使用,false表示仍有值需要生成,true表示迭代器已經(jīng)結(jié)束。

          • value 可以是任何 JS 值,它是向消費(fèi)者展示的值。

          當(dāng)done為true時(shí),可以省略value。

          組合

          迭代器和可以可迭代對(duì)象可以用下面這張圖來表示:

          你知道JavaScript中的可迭代對(duì)象與迭代器嗎

          事例

          基礎(chǔ)知識(shí)介紹完了,接著,我們來配合一些事例來加深我們的映像。

          范圍迭代器

          我們先從一個(gè)非?;镜牡鏖_始,createRangeIterator迭代器。

          我們手動(dòng)調(diào)用it.next()以獲得下一個(gè)IteratorResult。 最后一次調(diào)用返回{done:true},這意味著迭代器現(xiàn)在已被使用,不再產(chǎn)生任何值。

          function createRangeIterator(from, to) {   let i = from;    return {     next() {       if (i <= to) {         return { value: i++, done: false };       } else {         return { done: true };       }     }   } }  const it = createRangeIterator(1, 3);  console.log(it.next()); console.log(it.next()); console.log(it.next()); console.log(it.next());

          你知道JavaScript中的可迭代對(duì)象與迭代器嗎

          可迭代范圍迭代器

          在本文的前面,我已經(jīng)提到 JS 中的某些語句需要一個(gè)可迭代的對(duì)象。 因此,我們前面的示例在與for … of循環(huán)一起使用時(shí)將不起作用。

          但是創(chuàng)建符合迭代器和可迭代協(xié)議的對(duì)象非常容易。

          你知道JavaScript中的可迭代對(duì)象與迭代器嗎

          function createRangeIterator (from, to) {   let i = from    return {     [Symbol.iterator] () {       return this     },     next() {       if (i <= to) {         return { value: i++, done: false }       } else {         return { done: true }       }     }   } }  const it = createRangeIterator(1, 3)  for (const i of it) {   console.log(i) }

          無限序列迭代器

          迭代器可以表示無限制大小的序列,因?yàn)樗鼈儍H在需要時(shí)才計(jì)算值。

          注意不要在無限迭代器上使用擴(kuò)展運(yùn)算符(…),JS 將嘗試消費(fèi)迭代器,由于迭代器是無限的,因此它將永遠(yuǎn)不會(huì)結(jié)束。 所以你的應(yīng)用程序?qū)⒈罎?,因?yàn)閮?nèi)存已被耗盡

          同樣,for … of 循環(huán)也是一樣的情況,所以要確保能退出循環(huán):

          function createEvenNumbersIterator () {   let value = 0    return {     [Symbol.iterator] () {       return this     },     next () {       value += 2       return { value, done: false}     }   } }  const it = createEvenNumbersIterator()  const [a, b, c] = it console.log({a, b, c})  const [x, y, z] = it console.log({ x, y, z })  for (const even of it) {   console.log(even)   if (even > 20) {     break   } }

          你知道JavaScript中的可迭代對(duì)象與迭代器嗎

          關(guān)閉迭代器

          前面我們提到過,迭代器可以有選擇地使用return()方法。 當(dāng)?shù)髦钡阶詈蠖紱]有迭代時(shí)使用此方法,并讓迭代器進(jìn)行清理。

          for … of循環(huán)可以通過以下方式更早地終止迭代:

          • break

          • continue

          • throw

          • return

          function createCloseableIterator () {   let idx = 0   const data = ['a', 'b', 'c', 'd', 'e']    function cleanup() {     console.log('Performing cleanup')   }   return {     [Symbol.iterator]() { return this },     next () {       if (idx <= data.length - 1) {         return { value: data[idx++], done: false }       } else {         cleanup()         return { done: true }       }     },     return () {       cleanup()       return { done: true }     }   } }  const it = createCloseableIterator()  for (const value of it) {   console.log(value)   if (value === 'c') {     break   } }  console.log('n----------n')  const _it = createCloseableIterator(); for (const value of _it) {   console.log(value); }

          你知道JavaScript中的可迭代對(duì)象與迭代器嗎

          • 如果知道迭代器已經(jīng)結(jié)束,則手動(dòng)調(diào)用cleanup()函數(shù)。

          • 如果突然完成,則return()起作用并為我們進(jìn)行清理。

          【推薦學(xué)習(xí):javascript高級(jí)教程】

          贊(0)
          分享到: 更多 (0)
          網(wǎng)站地圖   滬ICP備18035694號(hào)-2    滬公網(wǎng)安備31011702889846號(hào)