前端知识梳理之JS数组篇
JS数组的高阶函数之基础篇
什么是高阶函数
概念非常简单,如下:
一个函数就可以接收另一个函数作为参数或者返回值为一个函数,这种函数就称之为高阶函数。
数组中的高阶函数
map
- 参数:接受两个参数,一个是回调函数,一个是回调函数的this值(可选)。
其中,回调函数被默认传入三个值,依次为当前元素、当前索引、整个数组。 - 创建一个新数组,其结果是该数组中的每个元素都调用一个提供的函数后返回的结果
- 对原来的数组没有影响
1 | let nums = [1, 2, 3]; |
当然,后面的参数都是可选的 ,不用的话可以省略。
reduce
- 参数: 接收两个参数,一个为回调函数,另一个为初始值。回调函数中三个默认参数,依次为积累值、当前值、整个数组。
1 | let nums = [1, 2, 3]; |
不传默认值会怎样?
不传默认值会自动以第一个元素为初始值,然后从第二个元素开始依次累计。
filter
参数: 一个函数参数。这个函数接受一个默认参数,就是当前元素。这个作为参数的函数返回值为一个布尔类型,决定元素是否保留。
filter方法返回值为一个新的数组,这个数组里面包含参数里面所有被保留的项。
1 | let nums = [1, 2, 3]; |
sort
参数: 一个用于比较的函数,它有两个默认参数,分别是代表比较的两个元素。
1 | let nums = [2, 3, 1]; |
当比较函数返回值大于0,则 a 在 b 的后面,即a的下标应该比b大。
反之,则 a 在 b 的后面,即 a 的下标比 b 小。
整个过程就完成了一次升序的排列。
当然还有一个需要注意的情况,就是比较函数不传的时候,是如何进行排序的?
答案是将数字转换为字符串,然后根据字母unicode值进行升序排序,也就是根据字符串的比较规则进行升序排序。
函数的arguments为什么不是数组?如何转化成数组?
因为argument是一个对象,只不过它的属性从0开始排,依次为0,1,2…最后还有callee和length属性。我们也把这样的对象称为类数组。
常见的类数组还有:
- 用getElementByTagName/ClassName/Name()获得的HTMLCollection.
- 用querySlector获得的nodeList
那这导致很多数组的方法就不能用了,必要时需要我们将它们转换成数组,有哪些方法呢?
Array.prototype.slice.call()
1 | function sum(a, b) { |
Array.from()
1 | function sum(a, b) { |
这种方法也可以用来转换Set和Map哦!
ES6展开运算符
1 | function sum(a, b) { |
利用concat+apply
1 | function sum(a, b) { |
当然,最原始的方法就是再创建一个数组,用for循环把类数组的每个属性值放在里面,过于简单,就不浪费篇幅了。
forEach中return有效果吗?如何中断forEach循环?
在forEach中用return不会返回,函数会继续执行。
1 | let nums = [1, 2, 3]; |
中断方法:
使用try监视代码块,在需要中断的地方抛出异常。
官方推荐方法(替换方法):用every和some替代forEach函数。every在碰到return false的时候,中止循环。some在碰到return ture的时候,中止循环.
JS判断数组中是否包含某个值
方法一:array.indexOf
此方法判断数组中是否存在某个值,如果存在,则返回数组元素的下标,否则返回-1。
1 | var arr=[1,2,3,4]; |
方法二:array.includes(searcElement[,fromIndex])
此方法判断数组中是否存在某个值,如果存在返回true,否则返回false
1 | var arr=[1,2,3,4]; |
方法三:array.find(callback[,thisArg])
返回数组中满足条件的第一个元素的值,如果没有,返回undefined
1
2
3
4
5 var arr=[1,2,3,4];
var result = arr.find(item =>{
return item > 3
});
console.log(result);
方法四:array.findeIndex(callback[,thisArg])
返回数组中满足条件的第一个元素的下标,如果没有找到,返回-1]
1
2
3
4
5 var arr=[1,2,3,4];
var result = arr.findIndex(item =>{
return item > 3
});
console.log(result);
当然,for循环当然是没有问题的,这里讨论的是数组方法,就不再展开了。
JS中flat—数组扁平化
对于前端项目开发过程中,偶尔会出现层叠数据结构的数组,我们需要将多层级数组转化为一级数组(即提取嵌套数组元素最终合并为一个数组),使其内容合并且展开。那么该如何去实现呢?
需求:多维数组=>一维数组1
2let ary = [1, [2, [3, [4, 5]]], 6];// -> [1, 2, 3, 4, 5, 6]
let str = JSON.stringify(ary);
调用ES6中的flat方法
1 | ary = arr.flat(Infinity); |
replace + split
1 | ary = str.replace(/(\[|\])/g, '').split(',') |
replace + JSON.parse
str = str.replace(/([|])/g, ‘’);
str = ‘[‘ + str + ‘]’;
ary = JSON.parse(str);
普通递归
1 | let result = []; |
利用reduce函数迭代
1 | function flatten(ary) { |
扩展运算符
1 | //只要有一个元素有数组,那么循环继续 |