谈谈遍历与迭代
其实遍历与迭代是意义很近的一组词,但为啥要要把它们都列出来呢?先要从遍历说起:
遍历在js中的形式
The for loop
for
循环是最普遍的遍历方式, 下面是一个简单的栗子;
|
|
for循环的不足之处就是必须维护计数器i与退出条件digits.length
, 对刚学习编程的人来说,
这可能有点困惑,不能一眼看出这是在做啥;
还有一点是for
循环很适合数组类型,但是js
不只是只有数组类型,因此for
循环不是一个所有类型的解决方案.
The for…in loop
for...in
循环优化了for循环的不足之处-需要维护计数器的变化与退出条件;
|
|
并且这对对象也是适用的,但是这个遍历方式也有一些问题:
正如上面code
中,遍历的是计数器,当需要每个value
值的时候,需要重新取值digits[index]
;
并且for…in会把所有的可枚举属性遍历出来,如增加到原型链上的方法,如下:
|
|
这也是for…in没有在js程序员中普遍流行的原因;
注意:forEach方法也是js遍历数组的一种方法,forEach实际上是一个数组方法,因而一般
适用在数组上,并且没有方法跳出循环;
for…of
直接看一个栗子:
for…of是针对集合(注意:非set而是collections),而不是所有的对象,适用范围是iterable对象;
什么是iterable对象?
迭代
程序员是一群不停折腾的物种,为了更加方便的遍历,在ES6引入了迭代协议;迭代协议有两种:
- iterable协议
- iterator协议
由于这次主题是讲遍历与迭代,所以只涉及第一种协议;
定义
什么是iterable, ECMA官方文档是如下定义的:
Property | Value | |
---|---|---|
[Symbol.iterator] | A zero arguments function that returns an object, conforming to the iterator protocol. |
也就是说只要具有[Symbol.iterator]属性,并且其值是一个0参数函数,这个函数执行返回的是一个符合iterator协议的对象,
符合上述条件的对象就是一个可迭代对象;
|
|
范围
目前JS内置的可迭代对象有String, Array, Map, Set, TypedArray, arguments等;需要注意的是普通的obj是不能迭代的;
几个用法
遍历:
|
|
适用于元素展开:
转换数组
转换成生成器