javascript 一些循环方法

本文介绍了JavaScript中多种数组遍历方法,包括for、forEach、map、filter、find、every、some、for in和for of。阐述了每种方法的使用场景、特点及性能,如for是基础循环,forEach用于修改数组项,map返回新数组等,还对比了for in和for of的区别。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

遍历数组有很多方法, 最简单的便是for循环, 另外还有forEach、map、filter、some、every、reduce等 ;
每种方法面向的场景是不一样的, 先讲一下使用, 性能嘛, 最后再看

for

for循环是最基础的一种循环方式

// 一般把长度先缓存, 避免重复获取, 无需多言
const arr = [1,2,3,4,5]
const len = arr.length;
for(i = 0; i < len; i++) {
	// do something
}

for循环可以通过breakreturn 等语句提前终止
for并没有块级作用域
当遇到return语句时 , 包含此for循环的方法会终止

const  gg = () => {
	const arr = [1,2,3,4,5]
	const len = arr.length
	for(i = 0; i < len; i++) {
		console.log(arr[i])
		if(i === 3) {
			return
		}
	}
	console.log('last')
}
// return 后 'last' 不打印
gg() // 1 2 3 4 

字符串同样有length属性, 所以可以遍历字符串

forEach

一般用于对数组每一项进行修改, 没有返回值

arr.forEach(_ => {
	// do something
})

由于break, continue只能在循环中使用, 而forEach回调function是函数
很明显不可以通过break, continue等中断循环
但是可以通过return结束本次循环

[1,2,3,4,5].forEach(_ => {
	if(_ === 3) {
		return 
	}
	console.log(_)
})
// 1 2 4 5
// 可以看到3 没有被打印, 循环仍会继续, 所以 4 5 被打印了

如果要我非要终止循环呢, 也不是不行, 不过我暂时只能想到抛异常的方法

try{
	[1,2,3,4,5].forEach(_ => {
		if(_ === 3) {
			throw new Error('end')
		}
		console.log(_)
	})
}catch(e){
	console.log(e)
}
// 1 2 
// throw new Error('end') 是一种方法

Set, Map原型中包含forEach方法, 所以可以用于遍历Set, Map, 并不需要 Array.forEach.call / apply 的方式去做

Set.prototype.forEach  // ƒ forEach() { [native code] }
Map.prototype.forEach  // ƒ forEach() { [native code] }

那么 Set 和 Map 调用 forEach 打印的 index, value都是什么呢

new Set(['one','two','three', NaN, NaN]).forEach((value, index, set) => {
	console.log(index)
	console.log(value)
})

//one
//one
//two
//two
//three
//three
//NaN
//NaN

// 可以看到, Set.forEach打印的index, value都是元素本身
// 题外话, 另一个有趣现象是, 我在new Set()传入了两个NaN, 由于Set不允许重复元素, 所以最后只会存在一个NaN值
// 但是, 不是说 NaN !== NaN 吗?  我认为, Set内部做了处理, 具体如何处理爹也不大明白

//--------------------------------------------------

//再看Map
new Map([["key1", "value1"], ["key2", "value2"]]).forEach((value, index, map) => {
	console.log(index)
	console.log(value)
})

//key1
//value1
//key2
//value2

//可以看到, index为元素的键, value为元素的值

map

一般是对每个元素进行一些处理, 并返回新的数组

arr.map((el, index) => {
	// do something with el
	return el
})

Set, Map没有该方法

常见用法

const arr = [{id: '46548', name: 'faker'}, {id: '46549', name: 'faker2'}]
const idList = arr.map(el => el.id)
console.log(idList)
// ['46548', '46549']

filter / find

filter 用来查找符合条件的元素集合
find 找到第一个符合条件的元素并返回, 找到后不再往下遍历

every / some

这两个方法更多地用在测试数组的个性
every 测试数组内的所有元素是否都能通过某个指定函数的测试, 最终返回布尔值, 只要有一个元素不通过则终止循环并返回 false

const arr = [10, 30, 8, 2, 6] 
let bool = arr.every(el => {
	return el % 2 === 0
})
bool // true
// 每个元素除以2余数都为0吗, 很明显, 是的

some测试是否至少有一个元素通过由提供的函数实现的测试, 最终返回布尔值, 只要有一个元素通过则终止循环并返回 true

const arr = [1, 2, 7, 11, 6] 
let bool = arr.some(el => {
	return el % 2 === 0
})
bool // true
// 至少有一个元素除以2余数为0吗, 很明显, 是的

for in

for in 循环可以遍历字符串、对象、数组,不能遍历 Set/Map, 并且只能拿到可枚举的(enumerable)属性
需要注意的是, in 可以拿到原型上的属性

let obj = {
	[Symbol('one')]: 22,
	one: 11,
	two: 22
}
obj.__proto__.name = "haha"
for(let v in obj){
	console.log(v)
}
// one, two, name
// 这里用symbol作为键时, 该属性是不可枚举的, 所以for in取不到

// 把one属性改为不可枚举
Object.defineProperty(obj, 'one', {
	enumerable: false
})
// 这个时候就取不到one了
for(let v in obj){
	console.log(v)
}
// two, name

还有, 如果给数组加上属性, 也会被迭代出来

const arr = [1,2,3]
arr.name = 'haha'
// name属性也会被遍历出来
for(let v in arr){
	console.log(v)
}
// 0,1,2,name

因为迭代的顺序是依赖于执行环境的,所以数组遍历不一定按次序访问元素。因此当迭代访问顺序很重要的数组时,最好用整数索引去进行for循环

for of

遍历Array可以采用下标循环,遍历Map和Set就无法使用下标。
为了统一集合类型,ES6标准引入了新的iterable类型,Array、Map和Set都属于iterable类型, 也就是可迭代对象
for of 循环不仅支持数组、大多数伪数组对象,也支持字符串遍历,此外还支持 Map 和 Set 对象遍历

let iterable = new Map([["a", 1], ["b", 2], ["c", 3]]);
for (let [key, value] of iterable) {
  console.log(key);
  console.log(value);
}
// a 
// 1
// b
// 2
...
...

区别
for…in 语句以原始插入顺序迭代对象的可枚举属性, 拿到的是键
for…of 语句遍历可迭代对象定义要迭代的数据, 拿到的是值

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值