js中遍历数组加到新数组_js中数组的循环与遍历forEach,map

对于前端的循环遍历我们知道有

针对js数组的forEach()、map()、filter()、reduce()方法

针对js对象的for/in语句(for/in也能遍历数组,但不推荐)

针对jq数组/对象的$.each()方法

在语法和参数上他们有什么不同呢?

1.forEach: array.forEach(function(currentValue,index,arr), thisValue)

2.map: array.map(function(currentValue,index,arr), thisValue)

3.filter: array.filter(function(currentValue,index,arr), thisValue)

4.reduce: array.reduce(function(total,currentValue,index,arr), thisValue)

5.$.each: $.each( object/array, function(index,elment) );//jQuery的遍历方法,这里先不多说

6.for/in: for (var key in object) { //... }

这些方法都是源于for的封装而来的,先来看看for是怎么循环一个数组的

var arr = [4,3,2,1];

var index = [];

var value = [];

var sum = 0;

for(var i=0;i

index.push(i);

value.push(arr[i])

sum += arr[i]

};

console.log(index); //[0, 1, 2, 3]

console.log(value); // [4,3,2,1]

console.log(sum); //10

//可以看出,i表示的是数组下标,arr[i]是通过下标来去的对应的值

forEach、map、filter、reduce方法相同点

**参数

4e380418332051f652a64545a501916d.png

forEach、map、filter、reduce参数.png

既然他们参数都是一样的,我们以forEach()求和为例,看看各个参数代表着什么

var arr = [4,3,2,1];

var sum = 0;

arr.forEach(function(val,index,arr){

console.log(val); //4

console.log(index); //0

console.log(arr); //[4,3,2,1]

console.log(arr[index]==val); // ==> true

sum+=val

});

console.log(sum); //10

从上可得,这几个方法中参数所代表的都是相同的。

关于参数还有一个点没说的是,reduce方法还有个参数,语法如下:

array.reduce(function(total, currentValue, index, arr), initialValue)

其中 currentValue, index, arr意义相同,而total代表计算的初始值, 也是计算结束后的返回值。

其中total, currentValue都是必须的参数。

对于计算一个数组的和,reduce就是很好的方法

var arr = [4,3,2.1,1.1];

var sum = arr.reduce(function(total, val) {

return total + Math.round(val);

});

console.log(sum);//10

**迭代时不做修改

这些方法处理数组时,数组元素的范围是在 callback 方法第一次调用之前就已经确定了。;若已经存在的元素被改变或删除了,则它们的传递到 callback 的值是 该方法遍历到它们的那一时刻的值;被删除的元素将不会被访问到。例如:

var words = ["one", "two", "three", "four"];

words.forEach(function(word) {

console.log(word);

if (word === "two") {

words.shift();

}

});

console.log(words);//["two", "three", "four"]

**兼容旧环境

这些方法都是ECMA5新增的数组方法,所以ie9以下都不支持,不过,可以从Array原型拓展从而实现以上全部功能,例如forEach方法:

if (typeof Array.prototype.forEach != "function") {

Array.prototype.forEach = function() {

/* 实现 */

};

}

下面来看看这几个方法不同的地方

定义:

forEach() forEach循环,循环数组中每一个元素并采取操作, 没有返回值, 可以不用知道数组长度

map函数,遍历数组每个元素,并回调操作,需要返回值,返回值组成新的数组,原数组不变

filter() 过滤通过条件的元素组成一个新数组, 原数组不变

reduce() 方法接收一个函数作为累加器,数组中的每个值(从左到右)开始缩减,最终计算为一个值

some函数,遍历数组中是否有符合条件的元素,返回Boolean值

forEachmapfilterreduce

操作

循环(迭代)

映射

过滤器

汇总

返回值

undefined

返回新数组

返回新数组

返回计算结果total

改变原数组?

看情况

检测空数组?

不检测

不检测

不检测

不检测

下面来看看这几个方法在应用中的不同:

1.对当前数组每个元素乘于100

1.for方法

var b = [1,2,3];

var f = [];

for(var i=0;i

f.push(b[i]*100)

};

console.log(f); //[100, 200, 300]

2.forEach方法:

var b = [1,2,3];

var f = []

b.forEach(function(v){

f.push(v*100)

});

console.log(f); //[100, 200, 300]

console.log(b); // [1, 2, 3]

2. forEach方法:

var b = [1,2,3];

b.forEach(function(item,index,arr){

arr[index] = item*100;

});

console.log(b); //[100, 200, 300]

3.map方法:

var b = [1,2,3];

var c = b.map(function(v){ return v*100} )

console.log(c); //[100, 200, 300]

4.for/in语句

var b = [1,2,3];

var f = [];

for(var k in b){

f.push(b[k]*100)

}

console.log(f); //[100, 200, 300]

2.对数组的求和

1.for循环

var arr = [1,2,3,4,5];

var sum = 0; //这里sum设置为0或null

for(i=0;i

sum += arr[i];

};

console.log(sum);//15

2.forEach方法

var arr = [1,2,3,4,5];

var sum = 0;

arr.forEach(function(v){

sum += v

})

console.log(sum);//15

3.map方法

//map不适合用来做和,因为他是对每个元素进行处理,再返回每个元素

4.for/in语句

var arr = [1,2,3,4,5];

var sum = 0;

for(var k in arr){

sum += arr[k]

};

console.log(sum); //15

3.js如何获取json对象数组中某个属性结合?

var arr = [

{a:1 ,b:2 ,c:3},

{a:4 ,b:5 ,c:6},

{a:7 ,b:8 ,c:9}

];

获取数组arr的a属性集合,有哪些方法?

1.for循环

var res = [];

for(var i=0;i

res.push(arr[i].a)

};

console.log(res); // [1, 4, 7]

2.forEach方法

var res3 = [];

arr.forEach(function(v){

res3.push(v.a);

});

console.log(res3); // [1, 4, 7]

3.map方法

var res2 = arr.map(function(v){

return v.a

});

console.log(res2); // [1, 4, 7]

4.for/in语句

var res4 = [];

for(var k in arr){

res4.push(k);

};

console.log(res4); // ["0", "1", "2"]

//for in 原本是遍历对象的,k为属性的键,所以k在这里为数组的下标。应改成如下

console.log('-----------------------');

var res5 = [];

for(k in arr){

res5.push(arr[k].a)

};

console.log(res5); //[1, 4, 7]

4.给json对象数组中的每个对象多加个字段

var users =[

{

lastName:'Li',

firstName:'Lei'},

{

lastName:'Han',

firstName:'Meimei'}

];

给其中每一个对象加一个fullName字段,就把lastName和firstName1.for循环for(var i = 0; i < users.length; i++){var user =users[i];

user.fullName= user.lastName +user.firstName;

}

代码是对的,但却不好(优秀),为什么?原因有2

创建了与主业务无关的for loop

创建了与主业务无关的变量i

用forEach的好处是什么?答案就是解决了上面那2个缺陷,代码如下:2.forEach方法

users.forEach(function(user, index, arr){

user.fullName= user.lastName +user.firstName;

});3.map方法var newUsers =users.map(function(v,i,arr){

v.fullName= v.lastName+v.firstName;returnv

});//主要如果这里return v.fullName = v.lastName+v.firstName;的话,得到的是["LiLei", "HanMeimei"]//注意: 此处的map会改变原始数组,因为给v多加了个属性v.fullName

从上我们可以看出,forEach,for/in,map都是封装了for循环,只是在应用的对象上稍有些不同,例如,

forEach主要数组的一些简单遍历

map主要是对数内每个元素的操作

for/in主要是对象键值的一些遍历

应用与细节

forEach方法

forEach的应用只要是数组的简单遍历,这里就不在多做阐述

map方法

map()对数组的每个元素进行一定的操作(映射)后,会返回一个新的数组;是处理服务器返回信息非常有用的函数。

求数组中每个元素的平方↓

只有一个参数来mapping一个数字数组

var res = [1,4,9].map(function(val){

return val*2 //[2,8,18]

});

求数组中每个元素的平方根↓

var numbers = [1, 4, 9];

var roots = numbers.map(Math.sqrt);

//roots的值为[1, 2, 3]

//numbers的值仍为[1, 4, 9]

使用map获取json数组中的某个属性集合

var users = [

{name:'zhou' ,email:'zhou@email.com'},

{name:'lin' ,email:'lin@email.com'},

{name:'wu' ,email:'wu@email.com'}

];

var emails = users.map(function(v){

return v.email

});

console.log(emails)

// ["zhou@email.com", "lin@email.com", "wu@email.com"]

使用map重新格式化对象数组中的对象↓

var arr= [

{key: 1, value: 10},

{key: 2, value: 20},

{key: 3, value: 30}

];

var reformattedArray = arr.map(function(obj) {

var rObj = {};

rObj[obj.key] = obj.value;

return rObj; //[{1: 10}, {2: 20}, {3: 30}]

});

//注意:

这里是return rObj整个对象,

如果是return rObj[obj.key] = obj.value; 值为[10,20,30]

可以看出以上map()的用法都是对集合里的每个元素做对应的实际的操作后,再返回到新的数组里。那如何使只对集合的某些元素做判断呢?返回的是什么,如下面例子:

在数组中取大于3的全部元素

[2, 3, 4, 5].map(function(val, key) {

return val > 3; //[false, false, true, true]

})

[2, 3, 4, 5].map(function(val, key) {

if(val > 3){ return val} //[undefined, undefined, 4, 5]

})

上面的结果都不是我们想要的,我们想要的只是纯粹的大于3的集合[4,5],对集合的每个元素进行判断,刷选出符合条件的元素,该怎么做呢?filter就是专为这种处理而生的。

filter方法

filter方法主要是对数组的筛选过滤,返回符合条件的元素,

例如,

------ 对于数组

// 筛选出大于3的数

[2, 3, 4, 5,10].filter(function(val, index) {

return val > 3; //[4,5]

})

// 筛选出能整除5的数

[2, 3, 4, 5,10].filter(function(val, index) {

return val % 5 == 0; //[5,10]

})

----- 对于json数组

筛选对象数组中含有‘orange’属性值的对象

var arr = [

{"name":"apple", "count": 2},

{"name":"orange", "count": 5},

{"name":"pear", "count": 3},

{"name":"orange", "count": 16},

];

1.filter方法

var newArr = arr.filter(function(item){

return item.name === "orange";

});

console.log(newArr);//

[{"name":"orange", "count": 5},

{"name":"orange", "count": 16}]

2.forEach方法

var newArr2 = [];

arr.forEach(function(v){

if(v.name === 'orange'){

newArr2.push(v)

}

});

console.log(newArr2);//

[{"name":"orange", "count": 5},

{"name":"orange", "count": 16}]

4.for循环

var newArr4 = [];

for(var i= 0, l = arr.length; i< l; i++){

if(arr[i].name === "orange" ){

newArr4.push(arr[i]);

}

}

console.log(newArr4); //

[{"name":"orange", "count": 5},

{"name":"orange", "count": 16}]

3.map方法

var newArr3 = arr.map(function(item){

return item.name === "orange";

});

console.log(newArr3);

//[false, true, false, true]

Console.log(‘-------------------------------’)

var newArr3 = arr.map(function(v){

if(v.name === 'orange'){ return v }

});

console.log(newArr3)

//

[

undefined,

{"name":"orange", "count": 5},

{"name":"orange", "count": 16},

undefined

]

reduce方法

(暂时还不大理解,暂不做解释,哈哈哈哈哈哈哈哈)

请移步到 js中的reduce()函数

上面的分析和举例,同一种功能不同方法的实现,主要是为了让大家理解每个方法的实现的内在原理(for循环),被封装后有什么差异,比如不同参数的值,返回结果,以便在以后的实际应用中能根据业务需求用更简便合适的方法来实现。

根据实际需求做合适的数据处理

有一组成绩,需做一些操作:

1 输出全部考生名字

1 成绩大于60记为及格,否则不及格

2 过滤出成绩大于60的数据

3 计算出总成绩

4 输出:"姓名:xx 成绩:1xx"格式

var grades= [

{name: "优优", grade: 92},

{name: "小渣", grade: 55},

{name: "小优", grade: 82}

]

grades.map(v => v.name)

// ["优优", "小渣", "小优"]

grades.map(v => v.grade > 60 ? '及格' : '不及格')

// ["及格", "不及格", "及格"]

grades.filter(v => v.grade > 60)

// [{name: "优优", grade: 92}, {name: "小优", grade: 82}]

grades.reduce((total, v, i, arr) => {

return total + v.grade

},0)

//229

grades.forEach((v, i, arr) => {

v.all = `姓名:${v.name}, 成绩:${v.grade}`

});

console.log(grades)

//[{name: "优优", grade: 92, all: "姓名:优优, 成绩:92"},

//{name: "小渣", grade: 55, all: "姓名:小渣, 成绩:55"},

//{name: "小优", grade: 82, all: "姓名:小优, 成绩:82"}]

//forEach方法会改变原始数组

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值