盤點JavaScript中的Iterable Object(可迭代對象)
一、概念
可迭代(Iterable) 對象是數組的泛化。這個概念是說任何對象都可以被定制為可在 for..of 循環中使用的對象。
數組是可迭代的。但不僅僅是數組,很多其他內建對象也都是可迭代的。
二、通過創建一個對象,就可以輕松地掌握可迭代的概念
1.字符串是可迭代的
數組和字符串是使用最廣泛的內建可迭代對象。
對于一個字符串,for..of 遍歷它的每個字符:
for (let char of "test") {
// 觸發 4 次,每個字符一次
alert( char ); // t, then e, then s, then t
}
對于代理對(surrogate pairs),它也能正常工作!
(譯注:這里的代理對也就指的是 UTF-16 的擴展字符)
let str = '????';
for (let char of str) {
alert( char ); // ??,然后是 ??
}
2. 顯式調用迭代器(如何顯式地使用迭代器?)。
將會采用與 for..of 完全相同的方式遍歷字符串,但使用的是直接調用。這段代碼創建了一個字符串迭代器,并“手動”從中獲取值。
let str = "Hello"; // 和 for..of 做相同的事//
for (let char of str)
alert(char);
let iterator = str[Symbol.iterator]();
while (true) {
let result = iterator.next();
if (result.done) break;
alert(result.value); // 一個接一個地輸出字符
}
注:
很少需要這樣做,但是比 for..of 給了更多的控制權。例如,可以拆分迭代過程:迭代一部分,然后停止,做一些其他處理,然后再恢復迭代。
3. Array.from
有一個全局方法 Array.from 可以接受一個可迭代或類數組的值,并從中獲取一個“真正的”數組。然后就可以對其調用數組方法了。
例:
let arrayLike = {
0: "Hello",
1: "World",
length: 2
};
let arr = Array.from(arrayLike); // (*)
alert(arr.pop()); // World(pop 方法有效)// World(pop 方法有效)
運行結果:
在 (*) 行的 Array.from 方法接受對象,檢查它是一個可迭代對象或類數組對象,然后創建一個新數組,并將該對象的所有元素復制到這個新數組。
現在用 Array.from 將一個字符串轉換為單個字符的數組:
let str = '????';// 將 str 拆分為字符數組
let chars = Array.from(str);alert(chars[0]); // ??
alert(chars[1]); // ??
alert(chars.length); // 2
運行結果:
注:
與 str.split 方法不同,它依賴于字符串的可迭代特性。
因此,就像 for..of 一樣,可以正確地處理代理對(surrogate pair)。(譯注:代理對也就是 UTF-16 擴展字符。)
另外一種表達方式
技術上來說,它和下文做了同樣的事:
let str = '????';
let chars = []; // Array.from 內部執行相同的循環
for (let char of str) {
chars.push(char);
}
alert(chars);
運行結果:
但 Array.from 精簡很多。
甚至可以基于 Array.from 創建代理感知(surrogate-aware)的slice 方法(譯注:也就是能夠處理 UTF-16 擴展字符的 slice 方法):
function slice(str, start, end) {
return Array.from(str).slice(start, end).join('');
}
let str = '??????';
alert(slice(str, 1, 3)); // ????// 原生方法不支持識別代理對(譯注:UTF-16 擴展字符)
alert(str.slice(1, 3)); // 亂碼(兩個不同 UTF-16 擴展字符碎片拼接的結果)
三、總結
本文基于JavaScript基礎。介紹了Iterable object(可迭代對象),應用 for..of 的對象被稱為 可迭代的。通過創建一個對象,詳細的講解了字符串是可迭代的。顯式調用迭代器,以及在實際中 Array.from的應用。
歡迎大家積極嘗試,有時候看到別人實現起來很簡單,但是到自己動手實現的時候,總會有各種各樣的問題,切勿眼高手低,勤動手,才可以理解的更加深刻。