You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何将JavaScript树形对象的所有节点转换为扁平数组?

优雅实现树形结构转扁平数组的方案

首先给出原始树形结构:

let tree = {
   id: 1, children: [
    {id: 2},
    {id: 3},
    {
     id: 4, children: [
      {id: 5},
      {id: 6},
      {
       id: 7, children: [
        {id: 8},
        {id: 9},
        {id: 10}
       ]
      }
     ]
    }
   ]
  }

需求是将其转换为包含所有节点的扁平数组,每个节点保留自身的children结构(若存在),最终结果示例:

let flattenedTree = [
  { id: 1, children: [ /* 所有子节点... */ ] },
  { id: 2 },
  { id: 3 },
  { id: 4, children: [ /* 所有子节点... */ ] },
  { id: 5 },
  { id: 6 },
  { id: 7, children: [ /* 所有子节点... */ ] },
  { id: 8 },
  { id: 9 },
  { id: 10 }
]

以下是几种无需多层嵌套的优雅实现方案:

方案一:递归实现(简洁直观)

递归是处理树形结构最自然的方式,代码简洁易读,适合层级不深的场景:

function flattenTree(node) {
  const result = [node];
  if (node.children) {
    node.children.forEach(child => {
      result.push(...flattenTree(child));
    });
  }
  return result;
}

// 使用示例
const flattenedTree = flattenTree(tree);

逻辑说明:先将当前节点加入结果数组,再递归处理每个子节点,将子节点的扁平结果展开后追加到数组中,没有冗余嵌套,逻辑清晰。

方案二:迭代实现(避免递归栈溢出)

如果树形结构层级极深,递归可能触发栈溢出,此时可借助栈或队列实现迭代遍历:

深度优先遍历(栈实现)

function flattenTreeIterative(node) {
  const stack = [node];
  const result = [];
  
  while (stack.length > 0) {
    const current = stack.pop();
    result.push(current);
    // 子节点倒序入栈,保证遍历顺序与递归一致
    if (current.children) {
      for (let i = current.children.length - 1; i >= 0; i--) {
        stack.push(current.children[i]);
      }
    }
  }
  
  return result;
}

广度优先遍历(队列实现)

若需要按层级顺序输出节点,可使用队列:

function flattenTreeBFS(node) {
  const queue = [node];
  const result = [];
  
  while (queue.length > 0) {
    const current = queue.shift();
    result.push(current);
    if (current.children) {
      queue.push(...current.children);
    }
  }
  
  return result;
}

逻辑说明:通过手动维护栈/队列控制遍历流程,彻底避免递归栈溢出问题,代码结构清晰,无多层嵌套。

方案三:Generator函数(灵活可控)

利用Generator函数可实现惰性遍历,按需获取节点,也能轻松转换为数组:

function* traverseTree(node) {
  yield node;
  if (node.children) {
    for (const child of node.children) {
      yield* traverseTree(child);
    }
  }
}

// 转换为数组
const flattenedTree = [...traverseTree(tree)];

逻辑说明:通过yield逐个返回节点,yield*递归调用自身处理子节点,语法简洁,还支持按需迭代(无需一次性加载所有节点)。

内容的提问来源于stack exchange,提问作者user17196717

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.23 07:54:18