您好,登錄后才能下訂單哦!
這篇文章給大家分享的是有關(guān)Javascript迭代器怎么用的內(nèi)容。小編覺得挺實(shí)用的,因此分享給大家做個(gè)參考,一起跟隨小編過來看看吧。
在JavaScript中,迭代器是一種設(shè)計(jì)模式,用于在容器對(duì)象上遍歷,就是依次拿到其中的數(shù)據(jù),js中的迭代器有一個(gè)next()方法,每次調(diào)用都會(huì)返回一個(gè)對(duì)象,語法為“next:function(){return{value,done}}”。
本教程操作環(huán)境:windows10系統(tǒng)、javascript1.8.5版、Dell G3電腦。
迭代器是一種設(shè)計(jì)模式,可在容器對(duì)象 如 鏈表、數(shù)組上遍歷,無需關(guān)心容器對(duì)象的內(nèi)存分配的實(shí)現(xiàn)細(xì)節(jié)。簡單的理解就是可以一個(gè)一個(gè)的依次拿到其中的數(shù)據(jù),類似一個(gè)移動(dòng)的指針,但是會(huì)告訴我們什么時(shí)候結(jié)束。這樣我們可以拿到數(shù)據(jù)之后可以做一些我們需要做的事情。
js 中的迭代器是什么樣子的
在javascript 中迭代器是一個(gè)特殊對(duì)象,這個(gè)迭代器對(duì)象有一個(gè)next()方法,每次調(diào)用都返回一個(gè)對(duì)象(結(jié)果對(duì)象)。結(jié)果對(duì)象有兩個(gè)屬性:一個(gè)是value,表示下一個(gè)將要返回的值;另一個(gè)是done,它是一個(gè)布爾類型的值,如果已經(jīng)迭代到序列中的最后一個(gè)值,則它為 true。迭代器還會(huì)保存一個(gè)內(nèi)部指針,用來指向當(dāng)前集合中值的位置,每調(diào)用一次next()方法,都會(huì)返回下一個(gè)可用的值,類似下面這個(gè)對(duì)象的結(jié)構(gòu)。
{ next: function () { return { value:'', done: true / false } } }
隨著javascript 語言的能力進(jìn)一步提升,新增了一些新的數(shù)據(jù)類型 如 Map、Set、WeakMap 等,為了這些不同的數(shù)據(jù)結(jié)構(gòu),可以統(tǒng)一的迭代,es6 增加了迭代協(xié)議這個(gè)東西。
迭代協(xié)議并不是新的內(nèi)置實(shí)現(xiàn)或語法,而是協(xié)議。這些協(xié)議可以被任何遵循某些約定的對(duì)象來實(shí)現(xiàn)。
迭代協(xié)議具體分為兩個(gè)協(xié)議:可迭代協(xié)議和迭代器協(xié)議。
簡單的理解就是在js 中任何對(duì)象只要滿足迭代協(xié)議就可以遍歷
可迭代協(xié)議
要成為可迭代對(duì)象, 一個(gè)對(duì)象必須實(shí)現(xiàn) @@iterator 方法。這意味著對(duì)象(或者它原型鏈上的某個(gè)對(duì)象)必須有一個(gè)鍵為 @@iterator 的屬性,可通過常量 Symbol.iterator 訪問該屬性:
簡單的理解,你想讓一個(gè)東西可以遍歷,那么這個(gè)東西要有一個(gè) @@iterator ,這個(gè)屬性可以通過Symbol.iterator 訪問
迭代器協(xié)議
迭代器協(xié)議定義了產(chǎn)生一系列值(無論是有限個(gè)還是無限個(gè))的標(biāo)準(zhǔn)方式。當(dāng)值為有限個(gè)時(shí),所有的值都被迭代完畢后,則會(huì)返回一個(gè)默認(rèn)返回值。
只有實(shí)現(xiàn)了一個(gè)擁有以下語義(semantic)的 next() 方法,一個(gè)對(duì)象才符合迭代器協(xié)議:
迭代過程
當(dāng)一個(gè)對(duì)象需要被迭代的時(shí)候(比如被寫入一個(gè) for...of 循環(huán)時(shí)),首先,會(huì)不帶參數(shù)調(diào)用它的 @@iterator 方法( 此時(shí)返回的是結(jié)構(gòu)是這樣的 { next: function () {}}),然后使用此方法返回的迭代器獲得要迭代的值(其實(shí)就是不斷的調(diào)用這個(gè)next()方法)
迭代總結(jié)
迭代協(xié)議可以總結(jié)為,一個(gè)東西要遍歷,必須滿足可迭代協(xié)議跟迭代器協(xié)議
可迭代協(xié)議:這個(gè)對(duì)象必須有@@iterator,可以通過Symbol.iterator 訪問
迭代器協(xié)議:是一個(gè)對(duì)象,這個(gè)對(duì)象的next() 函數(shù)返回一個(gè)對(duì)象,這個(gè)對(duì)象包括兩個(gè)屬性,一個(gè)是value,一個(gè)是done(boolean,是否是最后一個(gè)元素,done 為 true 時(shí) value 可省略)
也就是說 迭代器對(duì)象本質(zhì)上,就是一個(gè)指針對(duì)象。通過指針對(duì)象的next(),用來移動(dòng)指針。
對(duì)象是沒有實(shí)現(xiàn)迭代器,所以不能遍歷對(duì)象,為了可以實(shí)現(xiàn)對(duì)象的遍歷,我們需要在對(duì)象上實(shí)現(xiàn)上面說的迭代器,通常有兩種寫法,一種是傳統(tǒng)的寫法,這種需要自己去控制內(nèi)部的狀態(tài),另外一種是利用生成器函數(shù)返回的Generator的迭代器來實(shí)現(xiàn),代碼如下:
傳統(tǒng)寫法
let obj = { name: 'joel', adress: 'gz', [Symbol.iterator]: () => { // 這里不要用this, 因?yàn)槭莚eturn fn, this 會(huì)丟失 let index = -1, atrrList = Object.keys(obj); const objIterator = { next: () => { let result = '' index++ if (index < atrrList.length) { result = { value: atrrList[index], done: false } } else { result = { done: true } } return result } } return objIterator } } for (const item of obj) { console.log('atrrs:' + item + ',value:' + obj[item]) }
生成器函數(shù)寫法
// 為不可迭代的對(duì)象添加迭代器 let obj = { a: 1, b: 2 } obj[Symbol.iterator] = function* () { let keys = Object.keys(obj); //取到key值的長度 let len = keys.length; //定義循環(huán)變量 let n = 0; //條件判斷 while (n <= len - 1) { yield { k: keys[n], v: obj[keys[n]] }; n++ } } //返回的是個(gè)對(duì)象的key和value for (let { k, v } of obj) { console.log(k, v); }
感謝各位的閱讀!關(guān)于“Javascript迭代器怎么用”這篇文章就分享到這里了,希望以上內(nèi)容可以對(duì)大家有一定的幫助,讓大家可以學(xué)到更多知識(shí),如果覺得文章不錯(cuò),可以把它分享出去讓更多的人看到吧!
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場,如果涉及侵權(quán)請(qǐng)聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。