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

如何在未知层级的多维数组中查找指定值并删除对应对象?

解决任意层级嵌套数组的对象查找与删除问题

你的问题核心在于固定层级的循环无法适配未知深度的嵌套结构,解决这类问题最常用的方法是使用递归——因为每个子菜单(submenu)的结构和顶层的MenuItems完全一致,都是包含对象的数组,我们可以复用同一个处理逻辑来遍历所有层级。

方案1:原地修改数组(递归+倒序遍历)

这种方式直接修改原数组,适合需要保留原引用的场景:

// 递归函数:处理任意层级的对象数组,删除指定id的元素
function removeTargetItem(arr, targetId) {
  // 倒序遍历数组,避免splice删除元素后索引错乱
  for (let i = arr.length - 1; i >= 0; i--) {
    const currentItem = arr[i];
    
    // 如果当前元素是目标,直接删除
    if (currentItem.id === targetId) {
      arr.splice(i, 1);
      // 如果你的数据中id唯一,这里可以加return终止遍历;如果可能有多个相同id,就去掉return
      // return;
    } 
    // 如果当前元素有子菜单,递归处理子菜单
    else if (currentItem.submenu && Array.isArray(currentItem.submenu) && currentItem.submenu.length > 0) {
      removeTargetItem(currentItem.submenu, targetId);
    }
  }
}

// 你的点击事件方法
delClick(id) {
  // 从顶层MenuItems开始处理
  removeTargetItem(this.menu.MenuItems, id);
}

方案2:返回新数组(函数式+递归)

如果不想修改原数组,而是生成一个新的结构(更符合函数式编程思想,避免副作用),可以用filter结合递归:

// 递归函数:返回删除目标元素后的新数组
function removeTargetItem(arr, targetId) {
  return arr.filter(item => {
    // 不是目标元素时,处理它的子菜单
    if (item.id !== targetId) {
      // 如果有子菜单,递归更新子菜单
      if (item.submenu && Array.isArray(item.submenu)) {
        item.submenu = removeTargetItem(item.submenu, targetId);
      }
      return true;
    }
    // 是目标元素则过滤掉
    return false;
  });
}

// 你的点击事件方法
delClick(id) {
  // 替换原MenuItems为新数组
  this.menu.MenuItems = removeTargetItem(this.menu.MenuItems, id);
}

为什么递归能解决问题?

递归的本质是把复杂的嵌套问题拆解成重复的简单问题:

  1. 对于每一层的数组,我们只需要做两件事:检查当前元素是否是目标,或者递归处理它的子菜单。
  2. 不管嵌套多少层(比如你的示例中id=8在第4层),递归都会自动深入到最底层,不需要手动加多层循环。

对比你原有代码的优势

你之前的代码是硬编码了3层循环,一旦菜单结构新增一层嵌套,就必须手动添加新的循环块;而递归代码只需要维护一套逻辑,不管层级多深都能自动适配,扩展性和可维护性大幅提升。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.08 16:42:27