数组的方法 - map、reduce、filter、sort
map、reduce、filter、sort方法的共同之处就是方法的参数是一个函数,通过对这个"函数参数"内部作相应处理来改变当前数组以得到想要的数组。
1.map (that's speak in Chinese is '映射')
var arr = [1, 3, 5, 7, 9];
//简单的转换
var arr2 = arr.map(function() {
return 1;
});
console.log(arr); //[1, 3, 5, 7, 9]
console.log(arr2); //[1,1, 1, 1, 1]
//复杂转换
var arr3 = arr.map(function(x, y, z) {
//在转换之前先搞清楚函数参数对应参数的意义
console.log(this); //this ==> window
console.log(x); //1 3 5 7 9 ==> 数组的value值
console.log(y); //0 1 2 3 4 ==> 数组的index值
console.log(z); //[1, 3, 5, 7, 9] ==> 数组本身
return x*x;
})
console.log(arr3); //[1, 9, 25, 49, 81]
其实map方法有两个参数map(callbackFn, thisArg); thisArg参数指的是将callbackFn里的this指向thisArg。
2.reduce
var arr = [2, 4, 6, 8, 10];
//reduce不同于map方法,方法返回的是一个值而不是一个数组了。(毕竟不再是映射了嘛!)
var value1 = arr.reduce(function() {
return 1;
});
console.log(value1 ); //1
//那我们就让它的"函数参数"做点什么吧 - 数组内元素累加
var value2 = arr.reduce(function(firstValue, nextValue, currentIndex, array) {
console.log(firstValue);
console.log(nextValue);
console.log(currentIndex);
console.log(array);
return firstValue + nextValue;
});
console.log(arr); //[2, 4, 6, 8, 10]
console.log(value2); // 30
注意事项:
1.arr.reduce(callbackFn, [initialValue]) - 同样reduce方法也是有第二个参数的
initialValue 可选项,其值用于第一次调用callbackFn的第一个参数。
第一次调用callbackFn的第二个参数就是数组的第一个元素。
若没有,则第一次调用callbackFn的第一个参数是数组的第一个元素。
第一次调用callbackFn的第二个参数就是数组的第二个元素。
var arr = ['a', 'b', 'c'];
var value = arr.reduce(function(x, y) {
return x + y;
});
console.log(value); //'abc'
var value2 = arr.reduce(function(x, y) {
return x + y;
}, 'A');
console.log(value2); //'Aabc'
2.如果数组为空并且没有提供initialValue,会抛出TypeError。如果数组仅有一个元素(无论位置如何)并且没有提供initialValue,或者有提供initialValue,但数组为空,那么此唯一值将被返回并且callbackFn不会被执行。
var arr = [];
arr.reduce(function() {
return 1;
});
//Uncaught TypeError: Reduce of empty array with no initial value
arr.push('A');
var value = arr.reduce(function() {
return 1;
});
console.log(value); //'A' callbackFn未执行
arr.pop();
var value2 = arr.reduce(function() {
return 1;
}, 'A');
console.log(value2); //'A' callbackFn未执行
3.filter ( 过滤 )
filter的参数和map方法的参数一致,"函数参数"的参数也一致,就不啰嗦了。
//过滤 - 符合条件的留下,不符合的走人。
var arr = [{name: '小明', grade: 2},{name: '小红', grade: 99},{name: '小李', grade: 60}];
//boss不高兴,想要进行裁员,要求对业绩分不及格(包括60)的炒鱿鱼。
var arr2 = arr.filter(function(x) {
if (x.grade >60) {
console.log(x.name + '可以留下。');
return true;
} else {
console.log(x.name + '可以走了。');
return false;
}
});
console.log(arr2); //[Object] Object ==> {name: '小红', grade: 99};
console.log(arr); // [Object, Object, Object] 原数组未发生变化
小红说:‘老板,我辞职...’
4.sort ( 排序 )
var arr = [10, 20, 1, 2];
arr.sort();
console.log(arr); //[1, 10, 2, 20]
/*
造成以上排序结果的原因:
默认情况下,对字符串排序,是按照ASCII的大小比较的。
Array的sort方法默认把所有元素先转换为String再排序,jieguo'10'排在了'2'的前面,因为字符'1'比字符'2'的ASCII码小。
*/
//想要对数字进行由小到大排序
arr.sort(function(x, y) {
if (x < y) {
return -1;
} else if (x > y) {
return 1;
}
return 0;
});
console.log(arr); //[1, 2, 10, 20]
//想要对数字进行由大到小排序
arr.sort(function(x, y) {
if (x < y) {
return 1;
} else if(x > y) {
return -1;
}
return 0;
});
console.log(arr); //[20, 10, 2, 1]