JavaScript 数组详解:从入门到精通

什么是数组?

数组(Array)是 JavaScript 中用于按顺序存储一组数据的数据结构。每个数据称为"元素",每个元素有一个对应的"索引"(下标),索引从 0 开始。

数组的创建方式

1. 字面量创建(最常用)

js 复制代码
// 创建空数组
const emptyArray = [];

// 创建包含初始元素的数组(可混合不同类型)
const numbers = [1, 2, 3, 4, 5];
const mixedTypes = [1, "hello", true, null, { key: "value" }];

2. 构造函数创建

js 复制代码
// 创建空数组(不推荐,优先用 [])
const arr1 = new Array(); // 等价于 []

// 创建指定长度的空数组(元素为 empty,无法直接遍历)
const arr2 = new Array(5); // [empty × 5]

// 创建包含初始元素的数组(多个参数时)
const arr3 = new Array(1, 2, 3); // [1, 2, 3]
const arr4 = Array(4, 5, 6);     // 无需 new,效果相同

注意陷阱:

  • 单个数值参数 :new Array(3) 创建长度为 3 的空数组,而非包含元素 3 的数组。
javascript 复制代码
    const arr = new Array(3);
    arr.map(x => 0); // [empty × 3](map 无法处理 empty)

3.Array.of () 方法(ES6+)

js 复制代码
// 创建包含指定元素的数组(解决 Array() 的歧义)
const arr1 = Array.of(5);     // [5](单个参数不再表示长度)
const arr2 = Array.of(1, 2, 3); // [1, 2, 3]
  • 无论参数数量,均将参数作为数组元素。
  • 对比 Array(5)(创建长度为 5 的空数组),Array.of(5) 明确创建包含元素 5 的数组。

4. Array.from

js 复制代码
// 从类数组对象(如 arguments、DOM 节点列表)创建数组
const argsToArray = (a, b, c) => Array.from(arguments);
argsToArray(1, 2, 3); // [1, 2, 3]

// 从可迭代对象(如字符串、Set、Map)创建数组
const arr1 = Array.from("hello"); // ['h', 'e', 'l', 'l', 'o']
const arr2 = Array.from(new Set([1, 2, 2, 3])); // [1, 2, 3]

// 带映射函数:初始化数组并处理元素
const arr3 = Array.from({ length: 3 }, (_, i) => i * 2); // [0, 2, 4]

数组的基本属性和特性

  • length 属性
    表示数组的长度,可以手动修改。
    • 作用:返回数组的长度(元素个数)。
js 复制代码
const arr = [1, 2, 3];
arr.length; // 3
arr.length = 5; // 扩展数组:[1, 2, 3, empty × 2]
arr.length = 2; // 截断数组:[1, 2]
  • 稀疏数组
    索引不连续的数组(存在 empty 元素)。
js 复制代码
const sparse = [];
sparse[2] = 'c'; // [empty × 2, 'c']
  • 数组可以存放任意类型的数据

    js 复制代码
    let arr = [1, 'a', true, null, undefined, {x:1}, [2,3]];

数组的常用方法

1. 增删改查

方法 作用 示例
push 尾部添加元素 arr.push(4)
pop 尾部删除元素 arr.pop()
unshift 头部添加元素 arr.unshift(0)
shift 头部删除元素 arr.shift()
splice 任意位置增删改 arr.splice(1, 2, 'a', 'b')
slice 截取子数组(不改变原数组) arr.slice(1, 3)

2. 查找

方法 作用 示例
indexOf 查找元素索引 arr.indexOf(2)
lastIndexOf 从后往前查找索引 arr.lastIndexOf(2)
includes 是否包含某元素 arr.includes(2)
find 查找第一个符合条件的元素 arr.find(x => x > 2)
findIndex 查找第一个符合条件的索引 arr.findIndex(x => x > 2)

3. 遍历与转换

方法 作用 示例
forEach 遍历数组 arr.forEach(x => console.log(x))
map 返回新数组 arr.map(x => x * 2)
filter 过滤,返回新数组 arr.filter(x => x > 2)
reduce 累加/汇总 arr.reduce((a, b) => a + b)
some 是否有元素满足条件 arr.some(x => x > 2)
every 是否所有元素都满足条件 arr.every(x => x > 2)

4. 其他常用方法

方法 作用 示例
join 拼接为字符串 arr.join('-')
concat 合并数组 arr.concat(4,5)
reverse 反转数组 arr.reverse()
sort 排序 arr.sort((a, b) => a - b)
fill 填充 arr.fill(0, 1, 3)
flat 扁平化 arr.flat(2)
at 支持负索引 arr.at(-1)

数组的遍历方式

JavaScript 中的数组遍历方式多样,各有适用场景。

1. 传统 for 循环

语法:

javascript 复制代码
for (初始化; 条件; 迭代) {
  // 循环体
}

示例:

javascript 复制代码
const arr = [1, 2, 3];
for (let i = 0; i < arr.length; i++) {
  console.log(arr[i]); // 1, 2, 3
}

特点 :灵活性高,可控制索引增减(如反向遍历 i--);性能稳定,适合大型数组;但语法冗长,需手动维护索引。

2. for...in 循环

语法:

javascript 复制代码
for (const 索引 in 数组) {
  // 循环体
}

示例:

javascript 复制代码
const arr = ['a', 'b', 'c'];
for (const index in arr) {
  console.log(index, arr[index]); // '0' 'a', '1' 'b', '2' 'c'
}

特点 :遍历的 index 为字符串类型;会遍历数组原型链上的可枚举属性(如添加到 Array.prototype 的方法),因此不推荐用于数组遍历。

3. forEach 方法

语法:

javascript 复制代码
数组.forEach((元素, 索引, 原数组) => {
  // 处理每个元素
});

示例:

javascript 复制代码
const arr = [10, 20, 30];
arr.forEach((item, index) => {
  console.log(item, index); // 10 0, 20 1, 30 2
});

特点 :内置方法,无需手动维护索引;无法中断循环 (不能用 break 或 return 跳出,除非抛出异常);会跳过稀疏数组中的 empty 元素。

4. for...of 循环(ES6+)

语法:

javascript 复制代码
for (const 元素 of 数组) {
  // 循环体
}

示例:

javascript 复制代码
const arr = [100, 200, 300];
for (const item of arr) {
  console.log(item); // 100, 200, 300
}

特点 :直接遍历元素(非索引);支持 break、continue 控制循环;可遍历数组、字符串、Map、Set 等可迭代对象,是数组遍历的推荐方式之一。

5. 迭代方法(map/filter/reduce 等)

这类方法虽主要用于数据处理,但本质是遍历数组并返回新结果:

  • map:遍历并返回处理后的新数组

    javascript 复制代码
    const arr = [1, 2, 3];
    const doubled = arr.map(item => item * 2); // [2, 4, 6]
  • filter:遍历并返回符合条件的元素组成的新数组

    javascript 复制代码
    const evenNumbers = arr.filter(item => item % 2 === 0); // [2]
  • reduce:遍历并累积计算结果

    javascript 复制代码
    const sum = arr.reduce((total, item) => total + item, 0); // 6

特点:不修改原数组,返回新数组或计算结果;适合数据转换、过滤、聚合等场景。

6. some/every 方法

用于判断数组元素是否满足条件(遍历可中断):

  • some :只要有一个元素满足条件就返回 true

    javascript 复制代码
    const hasEven = arr.some(item => item % 2 === 0); // true
  • every :所有元素满足条件才返回 true

    javascript 复制代码
    const allPositive = arr.every(item => item > 0); // true

特点:找到符合条件的元素后会立即停止遍历,效率较高。

小结

  1. 创建 :字面量 [] 最直观;new Array(n) 会生成稀疏数组;Array.of/Array.from/... 拓展了灵活初始化与转换方式。
  2. 操作 :push/pop/unshift/shift/splice 负责增删改;indexOf/includes/find 负责查;map/filter/reduce 负责批量转换与聚合。
  3. 遍历 :
    • 精准控制用 for
    • 简洁元素用 for...of
    • 链式处理用 map/filter/reduce
    • 注意 for...in、稀疏数组和 empty 元素的坑。

一句话速记

数组的本质是"有序列表",掌握创建、遍历、处理三件套,就掌握了 80% 的数组实战。

相关推荐
程序员Sunday13 小时前
JavaScript 事件循环面试题,宏任务与微任务怎么执行|Sunday面试指南
开发语言·javascript·面试·校招·事件循环·程序员sunday
默_笙15 小时前
🌊 向量库和 ES 都查不出"关系",我只好给奶茶建了一张人脉网
前端·javascript
思无邪6616 小时前
用 AI 做 JS 逆向:从抓包到复现的完整方法论
开发语言·javascript·人工智能
福兮说17 小时前
浏览器里把 iPhone 的 HEIC 转成 JPG:Chrome 解不开、转完大了七成、拍摄时间全丢,六个坑实测
前端·javascript·图像处理·chrome·ios·iphone·heic
可乐鸡翅yeah_18 小时前
video.js 集成 hls.js 开发 M3U8 播放器,新手高频踩坑
开发语言·前端·javascript·后端·ecmascript·m3u8·音视频在线播放
用户1179536547820 小时前
TRAE vs Claude Code 性能对比:从代码生成、多文件重构到底层吞吐,谁更适合你的日常开发?
javascript
kill52221 小时前
useRef
前端·javascript·react.js
米多科技21 小时前
我做了一个 3D 虚拟世界基底,在上面再搭 3D 世界或元宇宙,事半功倍
javascript·人工智能·github
霍营_托尼21 小时前
纯前端播 40GB 本地视频?我把浏览器改造成了「磁盘流式」播放器
前端·javascript·音视频开发
西柚小萌新1 天前
【LLM&&AI应用开发 八股文】--4.2.Agent智能体(中)
前端·javascript·react.js