经典面试题-数组扁平化&展开多级数组

简介: 工作中针对部分嵌套了多层数组的数据,采用数组扁平化能提升代码的可阅读性同时面试过程中,通常也会被作为一道手写代码题。考察候选人对现有API的熟练度/语法糖和应变能力,通常会叫列出你能实现的所有方案

题目描述


简述:将多维数组转换为一维数组


1.Array.flat


这个方法是ES2019提供的API,可以直接将数组进行扁平化处理


Array.prototype.flat(arr,deep)

  • 参数1:arr 待操作的数组
  • 参数2:deep 展开深度
  • 默认:1
  • 返回:一个新的数组

深度可以指定为 Infinity,表示展开所有的层级


运行示例


console.log([1, [2], [3, [[4]]]].flat(Infinity)); // [1,2,3,4]
console.log([1, [2], [[3]].flat()); // [1,2,[3]]
console.log([1, [2], [[3]].flat(1)); // [1,2,[3]]


当然这个方法并不一定是面试官想要看到的方法。


2. 递归


2.1 常规递归


这个是比较常规的解法,实现方案很多,这里介绍一个简单的:


  1. 使用for...of遍历数组
  2. 判断每一项的类型,如果是数组则进行递归调用,否则直接加入数组


具体实现如下


function myFlat(arr) {
    let res = []
    // 遍历
    for (const a of arr) {
        // 判断是否是数组
        if(a instanceof Array){
            // 是,则递归调用
            res = res.concat(myFlat(a))
        }else{
            // 不是则直接放入
            res.push(a)
        }
    }
    return res;
}
console.log(myFlat([1, [2], [3, [[4]]]]));// [1,2,3,4]


2.2 reduce 递归


调用数组的reduce方法,结合concat方法进行:


  1. 对每一项进行判断,如果是数组则递归调用
  2. 否则使用concat进行合并,返回新数组


具体实现如下:


let a = [{ a: 1 }, { b: 2 }, 3, 4, 5, [6, [7, 8, [9]]]]
function myFlat(arr) {
    return arr.reduce((pre, cur) => {
        return pre.concat(Array.isArray(cur) ? myFlat(cur) : cur)
    }, [])
}
console.log(myFlat(a))
// [ { a: 1 }, { b: 2 }, 3, 4, 5, 6, 7, 8, 9 ]


3. replace + JSON.parse + JSON.stringify


这个是代码上比较简介的一个实现,但存在缺陷,如果字符串中的内容本身就包含[]就会直接被处理掉


步骤:


  1. 执行JSON.stringify
  2. 执行replace替换掉[]
  3. 再调用JSON.parse生成


function myFlat(arr) {
    arr = JSON.stringify(arr)
    arr = JSON.parse('[' + arr.replace(/\[|\]/g, '') + ']')
    return arr
}
let a = [{ a: 1 }, { b: 2 }, 3, 4, 5, [6, [7, 8, [9]]]]
console.log(myFlat(a))
// [ { a: 1 }, { b: 2 }, 3, 4, 5, 6, 7, 8, 9 ]


4. 扩展运算符+Array.some迭代


  • Array.prototype.some方法判断是否有一项符合条件
  • 如果有一项是数组则调用扩展运算符进行展开


具体实现如下


let a = [{ a: 1 }, { b: 2 }, 3, 4, 5, [6, [7, 8, [9]]]]
function myFlat(arr) {
    while (arr.some(Array.isArray)) {
        arr = [].concat(...arr)
    }
    return arr
}
console.log(myFlat(a))
// [ { a: 1 }, { b: 2 }, 3, 4, 5, 6, 7, 8, 9 ]


相关文章
|
3月前
|
C语言
【Amazon 面试题1】一个数组,里面得数出现的次数是偶数次,只有一个数出现的次数是奇数次,找出那个出现奇数次的数
本文介绍了解决Amazon面试题的一种方法,即在一个所有数字出现次数都是偶数,除了一个数字出现奇数次的数组中,利用异或运算的性质找出出现奇数次的数字,并提供了C语言实现的代码示例。
67 1
|
3月前
|
Java
Java 基础语法-面试题(54-63道)(数组+类+包)
Java 基础语法-面试题(54-63道)(数组+类+包)
45 16
|
4月前
|
存储 算法
经典的滑动窗口的题目 力扣 2799. 统计完全子数组的数目(面试题)
经典的滑动窗口的题目 力扣 2799. 统计完全子数组的数目(面试题)
|
5月前
|
开发框架 .NET
技术好文共享:面试题:找出数组中只出现一次的2个数(异或的巧妙应用)(出现3次)
技术好文共享:面试题:找出数组中只出现一次的2个数(异或的巧妙应用)(出现3次)
|
5月前
|
数据采集 算法 数据挖掘
LeetCode 题目 80:删除排序数组中的重复项 II【算法面试高频题】
LeetCode 题目 80:删除排序数组中的重复项 II【算法面试高频题】
|
6月前
|
C++
【一刷《剑指Offer》】面试题 14:调整数组顺序使奇数位于偶数前面
【一刷《剑指Offer》】面试题 14:调整数组顺序使奇数位于偶数前面
|
6月前
|
算法 C++
【一刷《剑指Offer》】面试题 8:旋转数组的最小数字
【一刷《剑指Offer》】面试题 8:旋转数组的最小数字
|
6月前
|
JavaScript 前端开发 索引
经典面试题数组常用的方法
### 1.数组常用方法之 push()(==改变原数组,产生新数组==) - `push` 是用来在数组的末尾追加一个元素,返回添加以后的长度 ```javascript var arr = [1, 2, 3] // 使用 push 方法追加一个元素在末尾 arr.push(4) console.log(arr) // [1, 2, 3, 4] var res = arr.push(1,2,3,34); res//8 ``` ### 2.数组常用方法之 pop()(==改变原数组,产生新数组==) - `po
68 1
|
6月前
|
机器学习/深度学习 算法
【力扣经典面试题】189. 轮转数组
【力扣经典面试题】189. 轮转数组
|
6月前
|
算法 C++ 索引
【力扣经典面试题】238. 除自身以外数组的乘积
【力扣经典面试题】238. 除自身以外数组的乘积