iterable

遍历Array可以采用下标循环,遍历MapSet就无法使用下标。为了统一集合类型,ES6标准引入了新的iterable类型,ArrayMapSet都属于iterable类型。

具有iterable类型的集合可以通过新的for ... of循环来遍历。

for ... in循环由于历史遗留问题,它遍历的实际上是对象的属性名称。一个Array数组实际上也是一个对象,它的每个元素的索引被视为一个属性。

当我们手动给Array对象添加了额外的属性后,for ... in循环将带来意想不到的意外效果:

var a = ['A', 'B', 'C'];
a.name = 'Hello';
for (var x in a) {
    alert(x); // '0', '1', '2', 'name'
}
  • 1
  • 2
  • 3
  • 4
  • 5

for ... in循环将把name包括在内,但Arraylength属性却不包括在内。

for ... of循环则完全修复了这些问题,它只循环集合本身的元素:

var a = ['A', 'B', 'C'];
a.name = 'Hello';
for (var x of a) {
    alert(x); 'A', 'B', 'C'
}
  • 1
  • 2
  • 3
  • 4
  • 5

然而,更好的方式是直接使用iterable内置的forEach方法,它接收一个函数,每次迭代就自动回调该函数。以Array为例:

var a = ['A', 'B', 'C'];
a.forEach(function (element, index, array) {
    // element: 指向当前元素的值
    // index: 指向当前索引
    // array: 指向Array对象本身
    alert(element);
});
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

SetArray类似,但Set没有索引,因此回调函数的前两个参数都是元素本身:

var s = new Set(['A', 'B', 'C']);
s.forEach(function (element, sameElement, set) {
    alert(element);
});
  • 1
  • 2
  • 3
  • 4

Map的回调函数参数依次为valuekeymap本身:

var m = new Map([[1, 'x'], [2, 'y'], [3, 'z']]);
m.forEach(function (value, key, map) {
    alert(value);
});
  • 1
  • 2
  • 3
  • 4

如果对某些参数不感兴趣,由于JavaScript的函数调用不要求参数必须一致,因此可以忽略它们。例如,只需要获得Arrayelement

var a = ['A', 'B', 'C'];
a.forEach(function (element) {
    alert(element);
});
  • 1
  • 2
  • 3
  • 4

推荐使用forEach方法来遍历集合元素,性能最高。

### 什么是 `iterable`? 在编程中,**iterable(可迭代对象)** 是指能够逐个返回其成员项的对象。它是一种抽象的概念,表示一个可以被遍历的对象集合,例如列表、元组、字典、字符串等。这些对象可以通过循环结构(如 `for` 循环)依次访问其中的每一个元素。 在 Python 中,只要一个对象定义了 `__iter__()` 方法,或者支持下标索引并实现了 `__getitem__()` 方法,就可以被认为是 iterable 对象。这意味着该对象可以通过内置函数 `iter()` 被转换为一个 iterator(迭代器),从而用于循环遍历[^3]。 ```python my_list = [1, 2, 3] for item in my_list: print(item) ``` 在上述代码中,`my_list` 是一个 iterable,因为它可以被用于 `for` 循环,并且每次迭代都会返回一个元素。 ### 如何实现一个自定义的 iterable? 要创建一个自定义的 iterable 类型,需要在类中定义 `__iter__()` 方法,该方法必须返回一个 iterator 对象。这个 iterator 对象本身也需要实现 `__next__()` 方法,以提供具体的遍历逻辑[^4]。 ```python class MyRange: def __init__(self, start, end): self.start = start self.end = end def __iter__(self): return self def __next__(self): if self.start >= self.end: raise StopIteration current = self.start self.start += 1 return current # 使用自定义的 iterable for num in MyRange(0, 5): print(num) ``` 在这个例子中,`MyRange` 类是一个 iterable,因为它实现了 `__iter__()` 方法。同时,它自身也是一个 iterator,因为它还实现了 `__next__()` 方法。 ### Iterable 的常见用途 - **数据处理与遍历**:iterable 最常见的用途是作为 `for` 循环的数据源,例如遍历文件行、数据库查询结果或网络请求响应。 - **函数式编程**:许多函数式编程工具,如 `map()`、`filter()` 和生成器表达式,都接受 iterable 作为输入参数。 - **构建高效数据流**:使用生成器(generator)等惰性求值的 iterable 可以有效减少内存占用,尤其是在处理大数据集时。 ### Iterable 与其他类型的区别 虽然 iterable 表面上看起来和序列(如列表、元组)类似,但它们的核心区别在于: - **序列**:支持索引访问,并且有固定的长度。 - **Iterable**:不一定支持索引,也不一定有固定长度。例如,生成器是一个 iterable,但它只能被遍历一次,并且不能回溯。 此外,不是所有的 iterable 都是可重复使用的。例如,某些生成器在遍历完成后就无法再次使用。 ### 内置函数对 iterable 的支持 Python 提供了许多内置函数可以直接操作 iterable,例如: - `min(iterable)`:返回 iterable 中的最小值。 - `max(iterable)`:返回最大值。 - `sum(iterable)`:计算总和。 - `any(iterable)` / `all(iterable)`:判断是否有任意/所有元素为真。 这些函数广泛应用于各种数据处理任务中,尤其是在处理大量数据时非常高效[^5]。 ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值