这是我第11篇简书。
一、操作
(一)Array.find/ Array.findIndex
-
find()
方法返回数组中满足提供的测试函数的第一个元素的值。否则返回undefined
-
findIndex()
方法返回数组中满足提供的测试函数的第一个元素的索引。否则返回-1
。
1.val是特定值
let obj = {}
obj = this.province.find(item => {
return item.value === val
})
2.传入一个回调函数,找到数组中符合当前搜索规则的第一个元素,返回它,并且终止搜索。
const arr = [1, "2", 3, 3, "2"]
console.log(arr.find(n => typeof n === "number")) // 1
(二)Array.filter
用于筛选数组中满足条件的元素,返回一个筛选后的新数组
过滤两个数组中相同的项
var a = [1, 2, 3, 4]
var b = [2, 3, 5]
// 筛选a中不包含b的元素的元素,返回新数组
a.filter(item => b.indexOf(item) === -1) // [1,
[1, 2, 3].filter(item => {return item > 2}) //[3]
(三)slice()和splice()
1、slice(start,end)
:方法可从已有数组中返回选定的元素,返回一个新数组,包含从start到end(不包含该元素)的数组元素(返回的新数组包含start,不包含end)。
- start参数:必须,规定从何处开始选取,如果为负数,规定从数组尾部算起的位置,-1是指最后一个元素。
- end参数:可选(如果该参数没有指定,那么切分的数组包含从start倒数组结束的所有元素,如果这个参数为负数,那么规定是从数组尾部开始算起的元素)。
注意:该方法不会改变原数组,而是返回一个子数组,如果想删除数组中的一段元素,应该使用Array.splice()
方法。
var arr = [1,2,3,4,5];
arr.slice(0,3); // [1,2,3]
arr.slice(1,3); // [2,3]
arr.slice(2); // [3,4,5]
2、splice()
:该方法向或者从数组中添加或者删除项目,返回被删除的项目。(该方法会改变原数组)
splice(index,howmany,item1,...itemX)
- index参数:必须,整数,规定添加或者删除的位置,使用负数,从数组尾部规定位置。
- howmany参数:必须,要删除的数量,如果为0,则不删除项目。
- tem1,...itemX参数:可选,向数组添加的新项目。
var arr = [1,2,3,4,5];
console.log(arr.splice(2,1,"hello")); // [3] 返回的新数组
console.log(arr); // [1, 2, "hello", 4, 5] 改变了原数组
console.log(arr.splice(1,2)); // [2,3]
console.log(arr); // [1, 4, 5]
(四)Array.from()
Array.from()
可以将类数组对象和可遍历对象(包括ES6新增的数据结构 Set 和 Map)转化为真正的数组。
从 String 生成数组:
Array.from('foo');
// [ "f", "o", "o" ]
从类数组对象(arguments)生成数组:
function fn() {
return Array.from(arguments);
}
fn(1, 2, 3);
// [ 1, 2, 3 ]
从 Set 生成数组:
set用来定义不重复数组的数据类型(es6)
const set = new Set(['foo', 'bar', 'baz', 'foo']);
Array.from(set);
// [ "foo", "bar", "baz" ]
从 Map 生成数组:
const map = new Map([[1, 2], [2, 4], [4, 8]]);
Array.from(map);
// [[1, 2], [2, 4], [4, 8]]
const mapper = new Map([['1', 'a'], ['2', 'b']]);
Array.from(mapper.values());
// ['a', 'b'];
Array.from(mapper.keys());
// ['1', '2'];
在 Array.from 中使用箭头函数:
Array.from([1, 2, 3], x => x + x);
// [2, 4, 6]
Array.from({length: 5}, (v, i) => i);
// [0, 1, 2, 3, 4]
数组去重合并:
function combine(){
let arr = [].concat.apply([], arguments); //没有去重复的新数组
return Array.from(new Set(arr));
}
var m = [1, 2, 2], n = [2,3,3];
console.log(combine(m,n)); // [1, 2, 3]
(五)map()
用于遍历数组,返回处理之后的新数组
arr = data.map(item => ({
id: item.id,
name: item.departmentName,
departmentId: item.departmentId,
corpid: item.corpid,
isLeaf: !item.isleaf
}))
arr.map(item => item * 2)
1.将string数组转换为number数组
let x1 = ['1','2'];
console.log(x1);
//["1", "2"]
x1 = x1.map(Number);
console.log(x1);
//[1,2]
2.将number数组转换为string数组
let x2 = [1,2];
console.log(x2);
//[1, 2]
x2 = x2.map(String);
console.log(x2);
//['1','2']
(六)reduce方法
reduce()
方法接收一个函数作为累加器,数组中的每个值(从左到右)开始缩减,最终计算为一个值。
reduce()
可以作为一个高阶函数,用于函数的 compose
。
注意: reduce()
对于空数组是不会执行回调函数的。
语法:
arr.reduce(function(prev,cur,index,arr){
}, initialValue);
arr 表示原数组;
prev 表示上一次调用回调时的返回值,或者初始值 initialValue;
cur 表示当前正在处理的数组元素;
index 表示当前正在处理的数组元素的索引,若提供 initialValue 值,则索引为0,否则索引为1;
initialValue 可选。传递给函数的初始值。可选0,也可选[]
// 求和
const arr = [1, 2, 3, 4, 5]
const sum = arr.reduce((pre, item) => {
return pre + item
}, 0) // 从数组第1项开始
console.log(sum) // 15
注:
reduceRight()
该方法用法与reduce()其实是相同的,只是遍历的顺序相反,它是从数组的最后一项开始,向前遍历到第一项。
(七)forEach()
用于遍历数组,无返回值。
// 一般第数组处理
dataList.forEach(item => {
arr.push(item)
})
// 加入筛选条件
datagroup.forEach(item => {
if (item.modelType === 2) {
personIds.push(item.id)
}
if (item.modelType === 1) {
departmentIds.push(item.departmentId)
}
})
//
data.forEach(item => {
let obj = {
...item,
name: item.departmentName,
id: item.departmentId
}
arr.push(obj)
this.dataObj[item.departmentId] = obj
})
(八)every()
用于判断数组中的每一项元素是否都满足条件,返回一个布尔值。
var isEvery = arr.every(function(item,index,array){
return item > 0;
});
console.log(isEvery);
// 是否更新全选
updateCheckAll(list) {
this.isCheckAll = list.every(item => item.checkeds)
}
(九)some()
用于判断数组中的是否存在满足条件的元素,返回一个布尔值。
let parendId = this.data.parentId
let isExist = this.parentDepartments.some(({ departmentId }) => {
return parseInt(departmentId) === parseInt(parendId)
})
item.isFullSelected = this.parentDepartments.some(
pd => pd.departmentId === item.departmentId
)
(10)补充
以上forEach()、map()、every()、some()和filter()
等除了传递一个匿名函数作为参数之外,还可以传第二个参数,该参数用于指定匿名函数内的this指向。
// 传两个参数
arr.forEach(function(item,index,array){
console.log(this); // 指向arr
},arr);
// 只传一个匿名函数的话,则this指向window
arr.forEach(function(item,index,array){
console.log(this); // window
});
二、数组的应用
1、数组去重
普通方法:
Array.prototype.distinct = function() {
var arr = this,
result = [],
i,
j,
len = arr.length;
for (i = 0; i < len; i++) {
for (j = i+1; j < len; j++) {
if (arr[i] === arr[j]) {
j = ++i;
}
}
result.push(arr[i]);
}
return result;
}
[1, 2, 3, 3, 4, 4].distinct(); // [1, 2, 3, 4]
reduce方法:
var new Arr = [1, 2, 3, 3, 4, 4].reduce(function (prev, cur) {
prev.indexOf(cur) === -1 && prev.push(cur);
}). [])
建议(骚)方法:
set用来定义不重复数组的数据类型
[...new Set([1, 2, 3, 3, 4, 4])] // [1, 2, 3, 4]
Array.from(new Set([1, 2, 3, 3, 4, 4])) // [1, 2, 3, 4]
2、排序
内置方法:
升序: [2, 1, 3, 4].sort((a, b) => a - b); // [1, 2, 3, 4]
降序: [1, 2, 3, 4].sort((a, b) => b - a); // [4, 3, 2, 1]
冒泡排序:
升序:
Array.prototype.bubleSort = function() {
let arr = this,
len = arr.length;
for (let outer = len; outer >= 2 ; outer--) {
for (let inner = 0; inner <= outer - 1; inner++) {
if (arr[inner] > arr[inner+1]) {
[arr[inner], arr[inner + 1]] = [arr[inner + 1], arr[inner]]
}
}
}
return arr;
}
[3, 4, 2, 1].bubleSort(); // [1, 2, 3, 4]
选择排序:
Array.prototype.selectSort = function() {
let arr = this,
len = arr.length,
i,
j;
for (i = 0; i < len; i++) {
for (j = i; j < len; j++) {
if (arr[i]) > arr[j]) {
[arr[i], arr[j]] = [arr[j], arr[i]];
}
}
}
return arr;
}
[3, 4, 2, 1].selectSort(); // [1, 2, 3, 4]
3、最大值
Math.max(...[1, 2, 3, 4]) // 4
Math.max.apply(this, [1, 2, 3, 4]) // 4
[1, 2, 3, 4].reduce( (prev, cur, curIndex, arr) => {
return Math.max(prev, cur);
}, 0)
4、求和
利用eval()函数:
-
eval()
函数会将传入的字符串当做 JavaScript 代码进行执行。
eval("2+3") // 5
eval([1,2,3,4].join('+')) // 10
利用reduce()
方法:
[1,2,3,4].arr.reduce((prev, cur) => prev + cur) //10
5、合并
[1,2,3,4].concat([5,6]) //[1,2,3,4,5,6]
[...[1,2,3,4],...[4,5]] //[1,2,3,4,5,6]
[1,2,3,4].push.apply([1,2,3,4],[5,6]) //[1,2,3,4,5,6]
6、判断是否包含某值
[1,2,3].includes(4) //false
[1,2,3].indexOf(4) //-1 如果存在换回索引
[1, 2, 3].find((item) => item===3 )) //3 如果数组中无值返回undefined
[1, 2, 3].findIndex((item) => item === 3)) //2 如果数组中无值返回-1
[1,2,3].some(item => { return item===3 }) // true
7、扁平化n维数组
(1)利用递归和数组合并方法concat实现扁平:
function flatten(arr) {
while(arr.some(item=>Array.isArray(item))) {
arr = [].concat(...arr);
}
return arr;
}
flatten([1,[2,3]]) //[1,2,3]
flatten([1,[2,3,[4,5]]) //[1,2,3,4,5]
(2)利用ES10
新api——Array.flat(n)
:
Array.flat(n)
是ES10
扁平数组的api,n表示数组嵌套的深度,如果数组嵌套两层,n取值大于或等于1都可以,n值为Infinity时维度为无限大。
[1,[2,3]].flat(1) //[1,2,3]
[1,[2,3,[4,5]].flat(1) //[1,2,3,4,5]
[1[2,3,[4,5[...]].flat(Infinity) //[1,2,3,4...n]
8、对象和数组转化
Object.keys({name:'张三',age:14}) //['name','age']
Object.values({name:'张三',age:14}) //['张三',14]
Object.entries({name:'张三',age:14}) //[[name,'张三'],[age,14]]
9、数组第每一项设置值
[1,2,3].map(() => 0) // [0, 0, 0]
[1,2,3].map(() => '') // ["", "", ""]
fill()
:
[1,2,3].fill(false) // [false,false,false]
注:fill填充对象会报错