Create by jsliang on 2019-07-31 11:22:27
Recently revised in 2019-08-15 16:00:00
数组 - 最简单的内存数据结构
一 目录
不折腾的前端,和咸鱼有什么区别
二 前言
如果小伙伴刚好看到这篇文章,想了解下 算法与数据结构 中,关于 数组 的知识。
那么,希望看到这篇文章的小伙伴拥有:
- 基本的 JavaScript 知识。
- 知道一点点的数组及其用法。
同时,希望看完这篇文章的小伙伴掌握:
- 数组基本常识
- 数组的增删改查
- 数组的常用知识点
但是,jsliang 无法确定小伙伴是否真具备上面知识点(前置条件),所以前言会简略介绍下数组,希望能先小科普一下,方便后面共同探讨。
如果小伙伴已经清楚数组相关基础知识点,可以跳过【前言】部分;
如果小伙伴不清楚或者想回顾下热热身,可以往下慢慢看。
更多精彩,欢迎小伙伴关注下方公众号或者前往 jsliang 的 GitHub:github.com/LiangJunron…
2.1 为什么用数组?
假设你写代码,列出星期一到星期日锻炼的时间,你可能会写成:
let Monday = 1,
Tuesday = 2,
Wednesday = 3,
Thursday = 4,
Friday = 5,
Saturday = 6,
Sunday = 7;
复制代码
这仅仅是一周的数据。
如果要你统计一年的数据,那样也太麻烦了,毕竟命名 365 个字段,会让人极度不适。
于是有了数组:
let exercise = [1, 2, 3, 4, 5, 6, 7];
复制代码
这不就变得简便了么。
2.2 如何创建和初始化数组?
let a = [];
let b = new Array();
复制代码
这样都是可行的。
如果你想初始化有长度的数组,或者数组一开始就有值:
let a = [1, 2, 3]; // [1, 2, 3]
let b = new Array(3); // [undefined, undefined, undefined]
let c = new Array([1, 2, 3]); // [1, 2, 3]
let d = new Array(3).fill(1); // [1, 1, 1]
let e = new Array(3).fill([]); // [[], [], []]
复制代码
当然,后面两个通过 fill()
创建的数组,推荐碰到 fill()
方法的时候再进一步了解。
变量 e 形成的数组会出问题的嗷~
2.3 如何访问数组?
let a = [1, 2, 3];
console.log(arr[0]); // 1
console.log(arr[1]); // 2
console.log(arr[2]); // 3
复制代码
记住数组的下标是从 0 开始的。
如果某个程序猿跟你表白说你是它心中第 0 位的人……你还是拒绝 “他” 吧,已经走火入魔没救了。
2.4 二维、三维乃至多维数组以及如何访问?
我们平时使用的 [1, 2, 3]
这种形式,称为一维数组。
而如果数组中嵌套数组,每嵌套多一层,就加一个维度,例如:
二维数组
let a = [[1, 2, 3], [4, 5]]; // 二维数组
// 访问二维数组
for (let i = 0; i < a.length; i++) {
for (let j = 0; j < a[i].length; j++) {
console.log(a[i][j]);
}
}
// 1
// 2
// 3
// 4
// 5
复制代码
三维数组
let b = [[1, 2, [3, 4]], [5, 6]]; // 三维数组
// 访问三维数组
for (let i = 0; i < b.length; i++) {
for (let j = 0; j < b[i].length; j++) {
for (let k = 0; k < b[i][j].length; k++) {
console.log(b[i][j][k]);
}
}
}
// 3
// 4
复制代码
至于多维数组,小伙伴可以自行推算。
2.5 来份案例热热身?
在这里,贴两份代码带大家热热身。
遍历斐波那契数列
const fibonacciSequence = [1, 1, 2, 3, 5, 8, 13];
for (let i = 0; i < fibonacciSequence.length; i++) {
console.log(fibonacciSequence[i]);
}
// 1 1 2 3 5 8 13
复制代码
实现斐波那契数列
const fibonacciSequence = [1, 1];
for (let i = 2; i < 20; i++) {
fibonacciSequence[i] = fibonacciSequence[i - 1] + fibonacciSequence[i - 2];
}
console.log(fibonacciSequence);
// [1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 377, 610, 987, 1597, 2584, 4181, 6765]
复制代码
2.6 悬难疑惑?
数组虽然是最简单的内存数据结构,但是有些坑还是需要注意的,以免深陷无法自拔,例如:传值和传址。
// 传值
let str1 = '1';
str2 = str1;
str2 = '2';
console.log(str1); // 1
console.log(str2); // 2
// 传址
let arr1 = [1, 2, 3];
arr2 = arr1;
arr2[0] = 4;
console.log(arr1); // [4, 2, 3]
console.log(arr2); // [4, 2, 3]
复制代码
问:jsliang 你怎么看传值和传址,能不能详细介绍下?
答:看下我那篇面试文章 jsliang 的 2019 面试准备 或者百度下相关知识点吧,毕竟咱主要目的不是讲这个知识点,在这里引出是为了让小伙伴们热热身。
如果小伙伴觉得非常有必要将热身写成详细清单,小伙伴记得私信我哈
更多的数组问题或者相关隐藏点,还是等我想起来或者小伙伴提到,我再进行补充吧。
三 数组的增删改查及其工作应用
提起 算法与数据结构,很多前端小伙伴可能第一时间反应:“卧槽这有卵用”,“为啥面试都搞这个,进去后还不是写 if...else...”……
enm...还真有用。
jsliang 结合数组的增删改查及其工作中的使用场景,跟你聊聊数组的妙用。
3.1 数组的新增操作
话不多说,关门,放、放代码:
let arr = [1, 2, 3];
// 通过 push() 方法
arr.push(4); // [1, 2, 3, 4]
// 通过 length 属性
arr[arr.length] = 5; // [1, 2, 3, 4, 5]
复制代码
数组新增元素的两种方式:
- 一种是通过
push()
方法,直接将元素添加到数组最后一位。 - 另一种是通过利用数组的
length
属性,该属性可以显示数组的长度,而arr[arr.length]
即给其最大长度后面再加一个长度。
既然上面我们通过两种方式,往数组后面插入了新元素,那么有没有方法,往数组前面插入新元素呢?
有!
let arr = [3, 4, 5];
// 通过 unshift 方法
arr.unshift(2); // [2, 3, 4, 5]
// 通过遍历数组
for (let i = arr.length; i >= 0; i--) {
arr[i] = arr[i - 1];
}
arr[0] = 1;
// [1, 2, 3, 4, 5]
复制代码
很好,通过这四种方式,我们就掌握了往数组头部和数组尾部新增元素。
那么,在工作中它们有何作用呢?
目前使用最多的是 push()
操作,通常用于给数组新增元素。
举例常见的场景:给 Table 新增一行数据。
数据内容 | |
---|---|
新增 | 第一行数据 - jsliang |
新增 | 第二行数据 - 梁渣渣 |
jsliang 尝试自己画了个表格,太小了不好贴图,就使用 Markdown 演示下好了。
如上,我们点击【新增】按钮的时候,就可以直接往 Table 下面新增一行数据。
而如果是 unshift()
,目前工作还未接触到,如果有碰到的小伙伴,欢迎贴出应用场景~
3.2 数组的删除和修改操作
首先,jsliang 觉得删除和修改操作在一定程度上利用的数组 API 非常一致,所以贴在一起写了:
- splice()
- slice()
- filter()
在这里,我们介绍三种方法进行操作。
3.2.1 删除和修改之 splice()
对于前端来说,数组的 splice()
方法是个万金油,它能适用于新增、修改、删除这些场景。
那么,如何利用 splice()
进行新增、修改和删除呢?
我们先了解下 splice()
特性:
var months = ['Jan', 'March', 'April', 'June'];
// 新增操作
months.splice(1, 0, 'Feb');
// ['Jan', 'Feb', 'March', 'April', 'June']
// 修改操作
months.splice(4, 1, 'May');
// ['Jan', 'Feb', 'March', 'April', 'May']
// 删除操作
months.splice(4, 1);
// ['Jan', 'Feb', 'March', 'April']
复制代码
如上,splice()
的语法是:array.splice(start, deleteCount, item1, item2, ...)
。
start
为数组的开始坐标deleteCount
为需要从开始坐标起,删除的个数,可以为 0,代表不删除item
为需要新增进去的元素。
那么,讲到这里,小伙伴们应该对 splice()
有深刻了解了。
下面我们讲讲 splice()
对于修改操作,在工作中的使用场景:
修改 Table 某行的数据
let list = [
{ id: '1', name: 'jsliang' },
{ id: '2', name: '梁峻荣' },
{ id: '3', name: 'JavaScriptLiang' },
];
function addData(rowIndex) {
list.splice(rowIndex, 0, {
id: '4',
name: '梁渣渣',
});
}
addData(1);
console.log(list);
// [
// { id: '1', name: 'jsliang' },
// { id: '4', name: '梁渣渣' },
// { id: '2', name: '梁峻荣' },
// { id: '3', name: 'JavaScriptLiang' },
// ]
复制代码
如上,我们希望将数据添加到指定位置(addData(n)
),这时候我们就使用了 splice()
对其进行操作,从而修改了原数组。
3.2.2 删除和修改之 slice()
而作为和 splice()
一个字母之差的 slice()
,又是何等的优秀呢?
首先,咱们科普下:
- splice():所进行的操作会影响到原数组
- slice():所进行的操作不会影响到原数组
什么意思呢?相信很多小伙伴在网上看数组相关攻略的时候,都会看到一堆的区分:这个方法会影响到原数组,这个方法不会影响到原数组……等等。
其实很容易理解:我想吃两块蛋糕,但是现在我只有一块蛋糕。如果我还惦记着自己的减肥,那么我可以将这款蛋糕切成两块,这样我就吃到两块蛋糕(影响到原数组);如果我觉得吃了两块蛋糕不会肥,那我就去照着这块蛋糕的样子,再买一块(不影响原数组)。
当然,这里都说是修改咯,slice()
还是有丢丢影响到数组的:
const str = 'jsliang';
str.slice(0, 2); // 'js'
str.slice(2); // 'liang'
复制代码
对于 slice()
来说,它的参数为:str.slice(beginSlice, endSlice)
。其中:
beginSlice
:从该索引(以 0 为基数)处开始提取原字符串中的字符。endSlice
:结束位置(以 0 为基数),如果不传,默认到数组末尾。
注意,
splice()
的第二个参数是影响到数组的个数,而slice()
的第二个参数是结束的位置,所以slice()
一般写法是:slice(index, index + length)
,即需要修改的位置(index),及其影响的长度(length)。
很好,说完这一堆废话,咱们讲讲工作中的使用场景:
let list = [
{ id: '1', name: 'jsliang' },
{ id: '2', name: '梁峻荣' },
];
function insertData(rowId) {
list = [
...list.slice(0, list.findIndex(item => item.id === rowId) + 1),
{
id: '3',
name: '',
},
...list.slice(list.findIndex(item => item.id === rowId) + 1),
]
}
insertData('1');
console.log(list);
// [
// { id: '1', name: 'jsliang' },
// { id: '3', name: '' },
// { id: '2', name: '梁峻荣' },
// ]
复制代码
还记得在上面我们说过用 slice()
做修改操作,也会影响到原数组 吗?是的,在这份代码我们可以看出,我们根据之前的数组,组合成一个新的数组,让这个元素指向了新的数组地址。
当然,这个并不重要,我们讲讲它的使用场景:在需要修改 Table 某行的时候,我们将其唯一值(id)传递了过去,然后方法 insertData
根据传递的 id 找到那一行,对其进行了修改。
如果你感觉并非那么容易理解,你可以尝试下将
rowId
换成index
,这是个明智的选择。
3.2.3 删除和修改之 filter()
首先,jsliang 对于 filter()
这个方法也不是很常使用:
我有个朋友,网名就叫 filter()
,每次使用它就跟使唤我朋友一样:“filter!我有事请你帮忙~”
但是,作为团队的一枚 螺丝钉,业务写得多了,你还是会接触到同事的代码的,所以还是有必要对其进行了解:
function isBigEnough(element) {
return element >= 10;
}
var filtered = [12, 5, 8, 130, 44].filter(isBigEnough);
// [12, 130, 44]
// 如果你喜欢用 ES6 的箭头函数
const number = [12, 5, 8, 130, 44];
const filterNumber = number.filter(item => item >= 10);
// [12, 130, 44]
复制代码
很好,讲到这里,我们就顺带科普下 filter()
这个方法了:
-
语法:
arr.filter(callback)
-
callback
:用来测试数组的每个元素的函数。返回true
表示该元素通过测试,保留该元素,false
则不保留。它会返回由通过元素组成的数组,或者是一个空数组 []。它接受以下三个参数:element
:数组中当前正在处理的元素index
:正在处理的元素在数组中的索引。array
:调用了filter
的数组本身。
所以一个比较完整的 filter()
可以这么写:
const number = [12, 5, 8, 130, 44];
const filterNumber = number.filter((item, index, array) => {
console.log(array);
return item >= 10 && index > 3;
});
// 输出 5 次 [12, 5, 8, 130, 44]
// 最终 filterNumber 的值为 [44]
复制代码
OK,介绍完毕,咱们看下应用场景:
let list = [
{ id: '1', name: 'jsliang' },
{ id: '2', name: '梁峻荣' },
{ id: '3', name: 'JavaScriptLiang' },
];
function changeData(id, newObj) {
list = [...list.filter(item => item.id !== id), newObj];
}
changeData('2', {
id: '4',
name: '梁渣渣',
});
[
{id: "1", name: "jsliang"},
{id: "3", name: "JavaScriptLiang"},
{id: "4", name: "梁渣渣"},
]
复制代码
这样,我们就将 id
为 2 的 梁峻荣
那行修改为 id
为 4 的 梁渣渣
。
3.3 数组的查询操作
上面讲完了新增、删除和修改,最后还是讲讲查询操作。
相比于上面的话题,查询的形式就多了。
例如说,我想知道数组中所有对象的 id:
let list = [
{ id: '1', name: 'jsliang' },
{ id: '2', name: '梁峻荣' },
{ id: '3', name: 'JavaScriptLiang' },
];
const ids = list.map(item => item.id);
// ["1", "2", "3"]
复制代码
无可厚非这也是一种查询,而且在工作中特实用,毕竟像 Ant Design 等,下拉框多选等情况,就需要将数据的 id 查找出来。
又或者说,我想知道 JavaScript
出现在哪个索引值下,它的 id 是多少:
let list = [
{ id: '1', name: 'jsliang' },
{ id: '2', name: '梁峻荣' },
{ id: '3', name: 'JavaScriptLiang' },
];
const id1 = list[list.findIndex(item => item.name === 'JavaScriptLiang')].id;
// '3'
// 当然有更快速的
const id2 = list.find(item => item.name === 'JavaScriptLiang').id;
// '3'
复制代码
当然,JavaScript 还有很多操作,可以查询数组中的数据。
当然,不管怎么说,jsliang 还是强烈推荐将这些方法记下来,然后在工作中不停尝试使用,这样你才会有所提升。
四 数组的常用知识点
下面开始无聊的 五年高考三年模拟 试题训练,希望小伙伴能在了解某个方法之后,通过其下面的 LeetCode 进行相应训练,从而熟练掌握数组的常用知识点。
4.1 push() - 末尾添加元素
push()
方法将一个或多个元素添加到数组的末尾,并返回该数组的新长度。
let arr = [1, 2, 3];
// 通过 push() 方法
arr.push(4); // [1, 2, 3, 4]
复制代码
实战 LeetCode:
- 000 - 字谜分组(puzzle-grouping)
- 020 - 有效的括号(valid-parentheses)
- 067 - 二进制求和(add-binary)
- 088 - 合并两个有序数组(merge-sorted-array)
- 118 - 杨辉三角(pascals-triangle)
4.2 unshift() - 开头添加元素
unshift()
方法将一个或多个元素添加到数组的开头,并返回该数组的新长度。
let arrA = ['1'];
arrA.unshift('0');
console.log(arrA); // ['0', '1']
let arrB = [4, 5, 6];
arrB.unshift(1, 2, 3);
console.log(arrB); // [1, 2, 3, 4, 5, 6]
复制代码
实战 LeetCode:
4.3 pop() - 末尾删除元素
pop()
方法从数组中删除最后一个元素,并返回该元素的值。此方法更改数组的长度。
let arr = [1, 2, 3, 4];
for(let i = 0, time = 1; i < arr.length; time++) {
console.log(`------\n第 ${time} 次遍历:`);
console.log(arr.pop());
console.log(arr);
}
/* Console:
------
第 1 次遍历:
4
[ 1, 2, 3 ]
------
第 2 次遍历:
3
[ 1, 2 ]
------
第 3 次遍历:
2
[ 1 ]
------
第 4 次遍历:
1
[]
*/
复制代码
实战 LeetCode:
- 007 - 整数反转(reverse-integer)
- 020 - 有效的括号(valid-parentheses)
- 189 - 旋转数组(rotate-array)
- 202 - 快乐数(happy-number)
- 225 - 用队列实现栈(implement-stack-using-queues)
4.4 shift() - 开头删除元素
shift()
方法从数组中删除第一个元素,并返回该元素的值。此方法更改数组的长度。
let str = [1, 2, 3];
console.log(str.shift()); // 1
console.log(str.shift()); // 2
console.log(str.shift()); // 3
console.log(str.shift()); // undefined
复制代码
实战 LeetCode:
- 014 - 最长公共前缀(longest-common-prefix)
- 171 - Excel表列序号(excel-sheet-column-number)
- 225 - 用队列实现栈(implement-stack-using-queues)
- 232 - 用栈实现队列(implement-queue-using-stacks)
4.5 splice() - 增删改元素
splice()
方法通过删除或替换现有元素或者原地添加新的元素来修改数组,并以数组形式返回被修改的内容。此方法会改变原数组。
var months = ['Jan', 'March', 'April', 'June'];
months.splice(1, 0, 'Feb');
console.log(months);
// ['Jan', 'Feb', 'March', 'April', 'June']
months.splice(4, 1, 'May');
console.log(months);
// ['Jan', 'Feb', 'March', 'April', 'May']
复制代码
实战 LeetCode:
- 026 - 删除排序数组中的重复项(remove-duplicates-from-sorted-array)
- 027 - 移除元素(remove-element)
- 088 - 合并两个有序数组(merge-sorted-array)
- 136 - 只出现一次的数字(single-number)
- 189 - 旋转数组(rotate-array)
4.6 concat() - 拼合两个数组
concat()
方法用于合并两个或多个数组。此方法不会更改现有数组,而是返回一个新数组。
const newArr = [1, 2, 3].concat(['a', 'b', 'c']);
// [1, 2, 3, 'a', 'b', 'c']
复制代码
实战 LeetCode:
4.7 filter() - 过滤数组元素
filter()
方法创建一个新数组, 其包含通过所提供函数实现的测试的所有元素。
function isBigEnough(element) {
return element >= 10;
}
var filtered = [12, 5, 8, 130, 44].filter(isBigEnough);
// [12, 130, 44]
复制代码
实战 LeetCode:
4.8 forEach() - 遍历操作原数组
forEach()
方法对数组的每个元素执行一次提供的函数。
const items = ['item1', 'item2', 'item3'];
const copy = [];
// 使用 for 遍历
for (let i = 0; i < items.length; i++) {
copy.push(items[i]);
}
// 使用 forEach 遍历
items.forEach(function(item){
copy.push(item);
});
复制代码
实战 LeetCode:
- 073 - 矩阵置零(set-matrix-zeroes)
- 350 - 两个数组的交集II(intersection-of-two-arrays-ii)
- 383 - 赎金信(ransom-note)
- 434 - 字符串中的单词数(number-of-segments-in-a-string)
4.9 join() - 数组转字符串
join()
方法将一个数组(或一个类数组对象)的所有元素连接成一个字符串并返回这个字符串。
var a = ['Wind', 'Rain', 'Fire'];
var myVar1 = a.join(); // myVar1 的值变为 "Wind,Rain,Fire"
var myVar2 = a.join(', '); // myVar2的值变为"Wind, Rain, Fire"
var myVar3 = a.join(' + '); // myVar3的值变为"Wind + Rain + Fire"
var myVar4 = a.join(''); // myVar4的值变为"WindRainFire"
复制代码
实战 LeetCode:
- 000 - 字谜分组(puzzle-grouping)
- 067 - 二进制求和(add-binary)
- 125 - 验证回文串(valid-palindrome)
- 190 - 颠倒二进制位(reverse-bit)
- 242 - 有效的字母异位词(valid-anagram)
4.10 indexOf() - 顺序查找第一个
indexOf()
方法返回调用 String 对象中第一次出现的指定值的索引。
'I am jsliang'.indexOf('a', 4); // 9
[1, 3, 1, 4].indexOf(1, 1); // 2
'怪盗 jsliang'.indexOf('我'); // -1
复制代码
实战 LeetCode:
- 001 - 两数之和(two-sum)
- 027 - 移除元素(remove-element)
- 028 - 实现strStr(implement-strstr)
- 205 - 同构字符串(isomorphic-strings)
- 217 - 存在重复元素(contains-duplicate)
4.11 lastIndexOf() - 倒序查找第一个
lastIndexOf()
方法返回指定元素(也即有效的 JavaScript 值或变量)在数组中的最后一个的索引,如果不存在则返回 -1。
var array = [2, 5, 9, 2];
var index = array.lastIndexOf(2); // 3
复制代码
实战 LeetCode:
暂无题目
4.12 map() - 遍历返回新数组
map()
方法创建一个新数组,其结果是该数组中的每个元素都调用一个提供的函数后返回的结果。
[1, 2, 3, 4].map(item => item * 2) // [2, 4, 6, 8]
[{
name: 'jsliang',
age: 24,
}, {
name: '梁峻荣',
age: 124
}].map((item, index) => {
return `${index} - ${item.name}`;
}) // ['0 - jsliang', '1 - 梁峻荣']
复制代码
实战 LeetCode:
- 001 - 两数之和(two-sum)
- 205 - 同构字符串(isomorphic-strings)
- 412 - FizzBuzz(fizz-buzz)
- 434 - 字符串中的单词数(number-of-segments-in-a-string)
4.13 reverse() - 反转数组元素
reverse()
方法将数组中元素的位置颠倒,并返回该数组。该方法会改变原数组。
let arr = [1, 2, 3];
arr.reverse();
console.log(arr); // [3, 2, 1]
复制代码
实战 LeetCode:
- 067 - 二进制求和(add-binary)
- 125 - 验证回文串(valid-palindrome)
- 171 - Excel表列序号(excel-sheet-column-number)
- 190 - 颠倒二进制位(reverse-bit)
- 344 - 反转字符串(reverse-string)
4.14 slice() - 查找指定位置元素
slice()
方法提取一个字符串的一部分,并返回一新的字符串。
const str = 'jsliang';
str.slice(0, 2); // 'js'
str.slice(2); // 'liang'
复制代码
实战 LeetCode:
- 005 - 最长回文子串(longest-palindromic-substring)
- 014 - 最长公共前缀(longest-common-prefix)
- 088 - 合并两个有序数组(merge-sorted-array)
- 459 - 重复的字符串(repeated-substring-pattern)
4.15 sort() - 数组排序
sort()
对数组的元素进行排序,并返回数组。
[4, 2, 5, 1, 3].sort(), // [1, 2, 3, 4, 5]
[4, 2, 5, 1, 3].sort((a, b) => a < b), // [5, 4, 3, 2, 1]
['a', 'd', 'c', 'b'].sort(), // ['a', 'b', 'c', 'd']
['jsliang', 'eat', 'apple'].sort(), // ['apple', 'eat', 'jsliang']
复制代码
实战 LeetCode:
- 268 - 缺失数字(missing-number)
- 389 - 找不同(find-the-difference)
- 414 - 第三大的数(third-maximum-number)
- 448 - 找出所有数组中消失的数字(find-all-numbers-disappeared-in-an-array)
- 455 - 分发饼干(assign-cookies)
4.16 toString() - 数组转字符串
toString()
返回一个字符串,表示指定的数组及其元素。
let arr = [1, 2, 3];
arr.toString(); // '1,2,3'
复制代码
实战 LeetCode:
- 190 - 颠倒二进制位(reverse-bit)
- 191 - 位1的个数(number-of-1-bits)
- 258 - 各位相加(add-digits)
- 443 - 压缩字符串(string-compression)
4.17 includes() - 数组包含某元素
includes()
方法用来判断一个数组是否包含一个指定的值,根据情况,如果包含则返回 true,否则返回 false。
[1, 2, 3].includes(2); // true
[1, 2, 3].includes(4); // false
[1, 2, 3].includes(3, 3); // false
[1, 2, 3].includes(3, -1); // true
[1, 2, NaN].includes(NaN); // true
复制代码
实战 LeetCode:
4.18 fill() - 填充数组
fill()
方法用一个固定值填充一个数组中从起始索引到终止索引内的全部元素。不包括终止索引。
let arr = [1, 2, 3, 4, 5];
arr = new Array(arr.length).fill(0);
// arr - [0, 0, 0, 0, 0];
复制代码
实战 LeetCode:
4.19 reduce() - 数组累计
reduce()
方法对数组中的每个元素执行一个由您提供的reducer函数(升序执行),将其结果汇总为单个返回值。
[1, 2, 3, 4].reduce((prev, next) => {
return prev + next;
}); // 10
['前端', 'pang', 'liang'].reduce((prev, next, index) => {
return (index = 0 ? '-js' : '') + prev + 'js' + next;
}); // 前端-jspang-jsliang
复制代码
实战 LeetCode:
- 014 - 最长公共前缀(longest-common-prefix)
- 202 - 快乐数(happy-number)
- 258 - 各位相加(add-digits)
- 268 - 缺失数字(missing-number)
- 049 - 字母异位词分组(group-anagrams)
4.20 find() - 查找数组元素
find()
方法返回数组中满足提供的测试函数的第一个元素的值。否则返回 undefined。
var inventory = [
{name: 'apples', quantity: 2},
{name: 'bananas', quantity: 0},
{name: 'cherries', quantity: 5}
];
function findCherries(fruit) {
return fruit.name === 'cherries';
}
inventory.find(findCherries));
// { name: 'cherries', quantity: 5 }
复制代码
实战 LeetCode:
暂无实战
4.21 findIndex() - 查找元素索引
findIndex()
方法返回数组中满足提供的测试函数的第一个元素的索引。否则返回-1。
var array1 = [5, 12, 8, 130, 44];
function isLargeNumber(element) {
return element > 13;
}
array1.findIndex(isLargeNumber); // 3
复制代码
实战 LeetCode:
暂无实战
五 总结
经过前面一系列的折腾,我们基本对数组的各种操作有所了解,虽然谈不上 精通,但是支持日常工作是毫无问题的了。
写到这里,jsliang 查询了下字数:36800。
是的,路漫漫其修远兮,就连我一开始写这篇文章的时候,我也没想到它有这么多的内容可以写,而且还是没有将一些 ES6、ES7 的数组新特性加上的情况下篇幅。
数组 - 最简单的内存数据结构,也是工作中最常使用的数据结构。
如果你觉得 jsliang 写得很 OK,欢迎点赞、留言、加微信好友、关注微信公众号等。
咱们,将继续探索,扎实编程基础,了解更多的数据结构和算法!
所有联系方式尽在:jsliang 的文档库
不折腾的前端,和咸鱼有什么区别!
jsliang 会每天更新一道 LeetCode 题解,从而帮助小伙伴们夯实原生 JS 基础,了解与学习算法与数据结构。
扫描上方二维码,关注 jsliang 的公众号,让我们一起折腾!
jsliang 的文档库 由 梁峻荣 采用 知识共享 署名-非商业性使用-相同方式共享 4.0 国际 许可协议进行许可。
基于github.com/LiangJunron…上的作品创作。
本许可协议授权之外的使用权限可以从 creativecommons.org/licenses/by… 处获得。