array.from 可将任意可迭代对象(如 nodelist、set、map、自定义实现 symbol.iterator 的类数组)转为真实数组,关键在于对象必须具备 symbol.iterator 方法并返回符合迭代器协议的对象,否则会报错“is not iterable”。

Array.from 可以将任何可迭代对象(包括实现了 Symbol.iterator 接口的类数组)转换为真正的 Array 实例,关键在于目标对象必须具备迭代能力,不一定要有 length 属性或数字索引。
确保类数组对象实现了 Symbol.iterator
只要对象拥有 [Symbol.iterator] 方法并返回一个迭代器,Array.from 就能遍历它。比如自定义一个类数组对象:
- 手动添加
[Symbol.iterator]方法,内部用yield或返回符合迭代器协议的对象 - 方法需返回一个具有
next()的对象,next()返回{ value, done } - Array.from 会自动调用该迭代器,逐个收集
value直到done: true
常见可直接转换的类数组示例
以下对象虽非 Array 构造,但自带 Symbol.iterator,Array.from 可直接处理:
-
document.querySelectorAll('div')—— NodeList(现代浏览器中默认可迭代) -
arguments对象(在非箭头函数中)—— 需手动部署迭代器或用其他方式兼容 - 字符串、Set、Map、TypedArray —— 它们都原生支持迭代,Array.from 能正确提取元素
自定义类数组并实现 Iterator 接口
例如定义一个只有 0、1、2 三个属性和 length: 3 的对象,但默认不可迭代。要让它能被 Array.from 使用,必须显式添加迭代器:
const arrayLike = {
0: 'a',
1: 'b',
2: 'c',
length: 3,
[Symbol.iterator]: function* () {
for (let i = 0; i const arr = Array.from(arrayLike); // ['a', 'b', 'c']
注意:不能只靠 length 和数字键;Array.from 不会像 Array.prototype.slice.call 那样“猜测”类数组结构,它只依赖迭代协议。
与扩展运算符 ... 的区别
Array.from(iterable) 和 [...iterable] 行为一致,都依赖 Symbol.iterator。区别在于:
- Array.from 支持第二个参数(映射函数),如
Array.from(iterable, x => x * 2) - 扩展运算符更简洁,但无法直接做映射,需配合其他方法
- 两者都要求目标是可迭代的;若对象仅有数字索引而无迭代器,会报错
is not iterable
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











