js数组用法大全

一 数组实例方法

1.1栈和队列方法

Javascript中这几个方法让数组可以直接作为栈(先进后出 FILO)和队列(先进先出 FIFO)这两种数据结构来使用(关于这两种数据结构可以参见http://c.biancheng.net/data_structure/stack_queue/),

使用push()和pop()可以让数组当成栈来使用,而使用shift()和push()可以数组当成队列来使用,另外还有一个unshift()方法(可以配合pop()模拟反向的队列)。

1.1.1 \color{red}{push()}

\color{red}{push()}方法可以接收任意数量的参数,将他们按照参数顺序添加到数组末尾,返回值是添加元素后数组的最新长度length

const array_1 = [1, 2, 3, 4];
console.log(array_1.push(5, 6)); // 6
console.log(array_1); // [ 1, 2, 3, 4, 5, 6 ]

1.1.2 \color{red}{pop()}

\color{red}{pop()}方法执行的是与push()方法相反的操作,将会删除数组的最后一项并返回该项(同时也length会减 1)。

const array_2 = [1, 2, 3, 4];
console.log(array_2.pop()); // 4
console.log(array_2); // [ 1, 2, 3 ]

1.1.3 \color{red}{shift()}

\color{red}{shift()}方法将会删除数组的第一项并返回该项(同时也length会减 1)。

const array_3 = [1, 2, 3, 4];
console.log(array_3.shift()); // 1
console.log(array_3); // [ 2, 3, 4 ]

1.1.4 \color{red}{unshift()}

另外的\color{red}{unshift()}方法执行的是与\color{red}{shift()}方法相反的操作,该方法可以接收任意数量的参数并按照参数的顺序添加到数组前,方法会返回新的数组长度length。

const array_4 = [1, 2, 3, 4];
console.log(array_4.unshift(-1, 0)); // 6
console.log(array_4); // [ -1, 0, 1, 2, 3, 4 ]

1.2 归并方法

Javascript中有两个归并方法reduce()和reduceRight()这两个方法都会遍历数组的每一项,并有一个最终返回值。

1.2.1\color{red}{ reduce()}

这个方法会接受两个参数:

第一个参数为针对每一项都会执行的归并方法:
这个方法可以接受四个参数:上一个归并值、当前项、当前项的索引和数组本身,这个函数的返回值将会作为下一次归并时该函数的第一个参数,所以当reduce()没有接收到可选的第二个参数时,归并将会从数组的第二项开始,

第二个参数为可选的以其为起点的初始值。

可以使用reduce()方法轻松执行数组求和的操作:

const array_1 = [1, 2, 3, 4];
console.log(array_1.reduce((prev, cur, index, array) => prev + cur)); // 10

1.2.2 \color{red}{reduceRight()}

而reduceRight()方法的操作与reduce()方法相同,只是遍历元素的方向是从最后一项到第一项而已,其余的没有任何区别。

const array_1 = [1, 2, 3, 4];
console.log(array_1.reduceRight((prev, cur, index, array) => prev + cur)); // 10

1.3 排序方法

sort()和reverse()都会返回调用它们的数组的引用,即此方法会改变原数组

1.3.1 \color{red}{sort()}

sort()方法可以接收一个可选的比较函数,用于判断哪个值应该被排在前面。这个比较函数接受两个参数,如果第一个参数想要被排在前面就返回一个负值,反之则返回一个正值。

const array_2 = [3, 1, 4, 2];
const compare = (a, b) => a - b; // 比较函数
array_2.sort(compare);
console.log(array_2); // [ 1, 2, 3, 4 ]

1.3.2 \color{red}{ reverse()}

reverse()方法会将调用它的数组元素反向逆序排列。

const array_1 = [1, 2, 3, 4];
array_1.reverse();
console.log(array_1); // [ 4, 3, 2, 1 ]

1.4 迭代方法

Javascript数组定义的迭代方法,分别是forEach()、map()、every()、some()和filter(),这几个方法都接受两个参数:以每一项为参数运行的函数callback,以及可选的作为函数运行上下文的作用域对象thisArg(即决定函数中this的值)。

而这个以每一项为参数运行的函数会接受三个参数:当前正在处理的数组元素currentValue、元素索引index和数组本身array。

1.4.1 \color{red}{forEach()}

forEach() 方法为数组中含有效值(已删除或者未初始化的项将被跳过)的每一项执行一次 callback 函数。forEach() 方法不会改变调用它的数组,没有返回值(或者说返回值是undefined)

// 注意:这里 array[2] = undefined, array[3] = null, array[4]未初始化
const array = [1, 2, undefined, null, , 3, 4];
// array[6] 被删除
array.pop();

// 已删除或者未初始化的项将被跳过,而 undefined 和 null 不会被跳过
array.forEach(function (value, index, array) {
  console.log(`value: ${value}, index: ${index}, array: ${array}`);
});
// value: 1, index: 0, array: 1,2,,,,3,4
// value: 2, index: 1, array: 1,2,,,,3,4
// value: undefined, index: 2, array: 1,2,,,,3,4
// value: null, index: 3, array: 1,2,,,,3,4
// value: 3, index: 5, array: 1,2,,,,3,4
// value: 4, index: 6, array: 1,2,,,,3,4

1.4.2 \color{red}{map()}

map()方法和forEach()有很多相似之处,比如都不会更改原始数组,但我们关注它们最大的区别:map()方法通过对每个数组元素执行函数来返回一个新的数组。

// 当回调函数仅使用 value 参数时,可以省略索引和数组参数:
const array_2 = [1, 2, 3, 4].map(value => {
  return value ** 2; // ES7新特性(2016):a ** b 指数运算符,它与 Math.pow(a, b)相同。
});
console.log(array_2); // [ 1, 4, 9, 16 ]

1.4.3 \color{red}{every()}

对数组的每一项都运行传入的函数,如果每一项函数都返回true,则every()方法返回true

let flag_every = [1, 2, 3, 4].every(value => value < 5);
console.log(flag_every); // true
flag_every = [1, 2, 3, 4].every(value => value < 3);
console.log(flag_every); // false

1.4.4 \color{red}{some()}

对数组的每一项都运行传入的函数,如果有一项函数返回true,则every()方法返回true

let flag_some = [1, 2, 3, 4].some(value => value > 3);
console.log(flag_some); // true
flag_some = [1, 2, 3, 4].some(value => value > 4);
console.log(flag_some); // false

1.4.5 \color{red}{filter()}

filter()方法(filter['fɪltər]: 过滤、筛选)创建一个包含通过测试的数组元素的新数组。

// 这里可以过滤出数组中的偶数元素
const array_5 = [1, 2, 3, 4].filter(value => value % 2 === 0);
console.log(array_5); // [ 2, 4 ]

1.5 操作方法

1.5.1 \color{red}{concat()}

concat()方法用于连接两个或多个数组。

该方法不会改变现有的数组,它首先会创建一个当前数组的副本,然后再把它的参数添加到副本末尾,最后返回这个新构建的数组。

传入数组参数将会被“打平”

const array_1 = [1, 2, 3];
console.log(array_1.concat(4, [5, 6]));
// [ 1, 2, 3, 4, 5, 6 ]

1.5.2 \color{red}{slice()}

slice()用于创建一个包含原有数组中一个或者多个元素的新数组,不会影响原数组。

slice()可以接收一个或者两个参数:

当只有一个参数时:slice()会返回从该索引开始(包括当前索引元素)到数组末尾的所有元素;

传入负值的话,将会按照数组长度length加上这个负值来确定位置
const array_2 = [1, 2, 3, 4, 5, 6];
console.log(array_2.slice(3)); // [ 4, 5, 6 ]
// 传入参数 -3 相当于传入 array_2.length - 3 = 3
console.log(array_2.slice(-3)); // [ 4, 5, 6 ]

如果传入两个参数,则slice()会返回从开始索引(包括当前索引元素)到结束索引(不包括结束索引位置的元素)对应的所有元素(相当于区间 [x, y) 内的元素),

同样,传入负值的话,将会按照数组长度length加上这个负值来确定位置
const array_2 = [1, 2, 3, 4, 5, 6];
console.log(array_2.slice(2, 4)); // [ 3, 4 ]
// 传入参数 (-4, -2) 相当于传入 (6 - 4 = 2, 6 - 2 = 4)
console.log(array_2.slice(-4, -2)); // [ 3, 4 ]

1.5.3 \color{red}{splice()}

splice()方法十分强大,它有许多使用方式。splice()的主要目的是在数组中间插入元素,此方法会改变原数组,有三种不同的方式去使用它:

删除
需要给\color{red}{splice()}传入两个参数:

要删除的第一个元素的位置
要删除的元素数量

const array_3 = [1, 2, 3, 4, 5];
array_3.splice(1, 2);
console.log(array_3); // [ 1, 4, 5 ]

插入
需要给\color{red}{splice()}传入三个参数

开始位置
0(代表要删除的元素数量为 0,即不删除)
要插入的元素,第三个参数之后可以传任意多个参数,将全部会被插入到数组中

// array_3 = [ 1, 4, 5 ]
array_3.splice(1, 0, "hello", "ienyh");
console.log(array_3); // [ 1, 'hello', 'ienyh', 4, 5 ]

替换
需要给\color{red}{splice()}传入三个参数

开始位置
1(代表要删除的元素数量为 1,即替换掉当前这个位置的元素)
替换的元素,同样第三个参数之后可以传任意多个参数,将全部会被插入到数组中

// array_3 = [ 1, 'hello', 'ienyh', 4, 5 ]
array_3.splice(3, 1, "world", "!");
console.log(array_3); // [ 1, 'hello', 'ienyh', 'world', '!', 5 ]

\color{red}{splice()}方法的返回值是一个数组,包含从原数组中删除的元素(没有删除元素将会返回空数组 [ ])

// [ 1, 'ienyh', 'hello', 'world', '!', 5 ]
// 从索引 1 开始删除 4 个元素
console.log(array_3.splice(1, 4)); // [ 'ienyh', 'hello', 'world', '!' ]
// 从索引 1 开始插入元素 2,3,4
console.log(array_3.splice(1, 0, 2, 3, 4)); // []
console.log(array_3); // [ 1, 2, 3, 4, 5 ]

1.5.4 \color{red}{flat()} ES10 新增(2019)

数组的成员有时还是数组,flat()用于将嵌套的数组“打平”,变成一维数组。该方法返回一个新数组,对原数组没有影响。

const array_1 = [1, 2, 3, [4, 5, 6]];
console.log(array_1.flat()); // [ 1, 2, 3, 4, 5, 6 ]

flat()默认只会“打平”一层,如果想要“打平”多层的嵌套数组,可以传一个整数给flat()方法作为参数,表示想要拉平的层数,默认为 1。

const array_2 = [1, 2, [3, 4, [5, 6]]];
console.log(array_2.flat()); // [ 1, 2, 3, 4, [ 5, 6 ] ]
console.log(array_2.flat(2)); // [ 1, 2, 3, 4, 5, 6 ]

如果想要将任意嵌套层数的数组“打平”,可以使用Infinity作为参数(Infinity 是全局对象(global object)的一个属性,即它是一个全局变量,初始值是 Number.POSITIVE_INFINITY)

const array_3 = [1, [2, [3, [4, [5, [6]]]]]];
console.log(array_3.flat(Infinity)); // [ 1, 2, 3, 4, 5, 6 ]

1.5.5 \color{red}{flatMap()} ES10 新增(2019)

flatMap()方法对原数组的每个成员执行一个函数,相当于执行map(),然后对返回值组成的数组执行flat()方法。该方法返回一个新数组,不改变原数组。

注意\color{red}{flatMap()}只能展开一层数组。

// 注意相当于 先执行 map() 然后 flat() “打平”
const array_4 = [1, 2, 3].flatMap(item => [item, item * 2]);
console.log(array_4); // [ 1, 2, 2, 4, 3, 6 ]

1.6 搜索和位置方法

1.6.1 \color{red}{indexOf()}

\color{red}{indexOf()}\color{red}{lastIndexOf()}\color{red}{includes() }这三个方法都可以接受两个参数:要查找的元素和一个可选的起始搜索位置(搜索时包含当前位置)。

\color{red}{indexOf()}方法从数组开头(即第一项)开始查找,返回查找到的第一个元素在数组中的位置(即数组下标),没找到将返回-1

const array_1 = [1, 2, 3, 4, 3, 2, 1];
console.log(array_1.indexOf(3)); // 2
console.log(array_1.indexOf(3, 3)); // 4
console.log(array_1.indexOf(5)); // -1

1.6.2 \color{red}{lastIndexOf()}

\color{red}{lastIndexOf()}方法用法一致,从数组末尾(即最后一项)开始查找,返回查找到的第一个元素在数组中的位置(即数组下标),没找到将返回-1

1.6.3 \color{red}{includes() } ES7 新增(2016)

\color{red}{includes() }方法返回一个布尔值(boolean),表示该数组是否包含要查找的元素

\color{red}{includes() }方法在比较时使用完全相等===

// array_1 = [1, 2, 3, 4, 3, 2, 1];
console.log(array_1.includes(3)); // true
console.log(array_1.includes(3, 5)); // false

1.6.4 \color{red}{find()}

\color{red}{find()}方法的参数和数组的迭代方法的参数一样,返回数组中满足提供的测试函数(callback)的第一个元素的值

\color{red}{find()}方法对数组中的每一项元素执行一次 callback 函数,直至有一个 callback 返回 true。当找到了这样一个元素后,该方法会立即返回这个元素的值,否则返回 undefined

// array_1 = [1, 2, 3, 4, 3, 2, 1];
const number_1 = array_1.find(value => value > 2);
console.log(number_1); // 3

1.6.5 \color{red}{findIndex()}
\color{red}{findIndex()}方法返回数组中满足提供的测试函数(callback)的第一个元素的索引(注意区别返回的是索引)。若没有找到对应元素则返回-1。

// array_1 = [1, 2, 3, 4, 3, 2, 1];
const number_2 = array_1.findIndex(value => value > 2);
console.log(number_2); // 2

二、然后是 Array 的静态方法

2.1 \color{red}{Array.from()}

\color{red}{Array.from()}方法可以接受最多三个参数,第一个参数为一个类数组对象(即可迭代,或者是有length属性同时存在可索引属性),第二个参数为可选参数,是一个映射函数参数,还有可选的第三个参数,用于指定映射函数参数中的this指向。

\color{red}{Array.from()}方法可以传入的参数包括数组、Map和Set的实例等

const arr = Array.from([1, 2, 3, 4, 5]); // 传入一个数组
console.log(arr); // [ 1, 2, 3, 4, 5 ]

const str = Array.from("ienyh"); // 传入字符串将会被转化为字符数组
console.log(str); // [ 'i', 'e', 'n', 'y', 'h' ]

const _map = new Map().set(1, 2).set(3, 4); // Map(2) { 1 => 2, 3 => 4 }
const _set = new Set().add(1).add(2).add(3).add(4); // Set(4) { 1, 2, 3, 4 }
console.log(Array.from(_map)); // [ [ 1, 2 ], [ 3, 4 ] ]
console.log(Array.from(_set)); // [ 1, 2, 3, 4 ]

\color{red}{Array.from()}方法也可以传入arguments和可迭代对象

function func() {
  return Array.from(arguments);
}
console.log(func(1, 2, 3, 4, 5)); // [ 1, 2, 3, 4, 5 ]

const obj = {
  0: 0,
  1: 1,
  2: 2,
  3: 3,
  length: 4,
};
console.log(Array.from(obj)); // [ 0, 1, 2, 3 ]

\color{red}{Array.from()}方法还可以用于对现有数组进行深拷贝(关于深浅拷贝可以参见文章【JS】深拷贝与浅拷贝的区别,实现深拷贝的几种方法)

const arr_1 = [1, 2, 3, 4];
const arr_2 = arr_1;
const arr_3 = Array.from(arr_1);
arr_1[0] = 0;
console.log(arr_2); // [ 0, 2, 3, 4 ]
console.log(arr_3); // [ 1, 2, 3, 4 ]
console.log(arr_1 === arr_3); // false

2.2 \color{red}{Array.of()}

\color{red}{Array.of()}方法用于将一组参数转化为数组,这个方法可以用于替代ES6之前常用的 \color{red}{Array.prototype.slice.call(arguments)},对比起来这种方法就显得有些繁杂了

const arr_4 = Array.of(1, 2, 3, 4);
const arr_5 = Array.of(1, "2", true, undefined);
console.log(arr_4); // [ 1, 2, 3, 4 ]
console.log(arr_5); // [ 1, '2', true, undefined ]

(我只是\color{red}{copy}的)
原文链接:https://blog.csdn.net/qq_45265059/article/details/116942489

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 199,393评论 5 467
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 83,790评论 2 376
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 146,391评论 0 330
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 53,703评论 1 270
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 62,613评论 5 359
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,003评论 1 275
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,507评论 3 390
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,158评论 0 254
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,300评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,256评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,274评论 1 328
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,984评论 3 316
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,569评论 3 303
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,662评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,899评论 1 255
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,268评论 2 345
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 41,840评论 2 339

推荐阅读更多精彩内容