Javascript复杂数组过滤器

Javascript复杂数组过滤器,javascript,angular,Javascript,Angular,我有一个对象数组,所有对象都有嵌套数组,每个元素都有另一个数组,每个元素都有一个数组,你就知道了。深嵌套数组 让我通过一个例子来解释我试图实现的目标。我有一份小组名单。每个小组都有一份英雄名单,每个英雄都有一份力量列表,每个力量都有一份力量列表 我希望能够使用mat stepper来迭代每一步,选择团队,然后是英雄,然后是力量,最后是力量。因此,当从垫子选择中选择一个组时,在下一步中,垫子选择将只保留属于该组的英雄,依此类推,直到力量 此组列表的示例如下所示: [ { "id": "

我有一个对象数组,所有对象都有嵌套数组,每个元素都有另一个数组,每个元素都有一个数组,你就知道了。深嵌套数组

让我通过一个例子来解释我试图实现的目标。我有一份小组名单。每个小组都有一份英雄名单,每个英雄都有一份力量列表,每个力量都有一份力量列表

我希望能够使用mat stepper来迭代每一步,选择团队,然后是英雄,然后是力量,最后是力量。因此,当从垫子选择中选择一个组时,在下一步中,垫子选择将只保留属于该组的英雄,依此类推,直到力量

此组列表的示例如下所示:

[
  {
    "id": "g1",
    "group": "1",
    "heroes": [
      {
        "id": "g1h1",
        "hero": "hero1",
        "powers": [
          {
            "id": "g1h1p1",
            "power": "pyromancy",
            "strengths": [
              {
                "id": "g1h1p1s1",
                "strength": "undead"
              }
            ]
          },
          {
            "id": "g1h1p2",
            "power": "light",
            "strengths": [
              {
                "id": "g1h1p2s1",
                "strength": "shadow people"
              },
              {
                "id": "g1h1p2s2",
                "strength": "guidence"
              }
            ]
          }
        ]
      },
      {
        "id": "g1h2",
        "hero": "hero2",
        "powers": []
      }
    ]
  },
  {
    "id": "g2",
    "group": "2",
    "heroes": [
      {
        "id": "g2h1",
        "hero": "hero1",
        "powers": [
          {
            "id": "g2h1p1",
            "power": "electromancy",
            "strengths": [
              {
                "id": "g2h1p1s1",
                "strength": "metal armor"
              },
              {
                "id": "g2h1p1s2",
                "strength": "metal shields"
              }
            ]
          },
          {
            "id": "g2h1p2",
            "power": "invisibility",
            "strengths": []
          }
        ]
      }
    ]
  },
  {
    "id": "g3",
    "group": "group3",
    "heroes": []
  }
]
列表中的每个元素都有自己唯一的id。好消息是我已经实现并正在工作。然而,我希望能够筛选的基础上,所有已准备好的选择,以及只有那些实力的选择

因此,拆除要求如下:

  • 如果强度已全部添加到选定强度列表中,则将其作为可能的选择删除
  • 如果某个元素在任何时候都有一个空列表,则将其作为可能的选择删除。因此,如果一个异能没有力量,或者英雄没有力量,那么移除它们
因此,使用上面的示例,如果我选择的列表all ready包含不死生物阴影人物金属盾牌(id值,而不是实际文本),那么我期望返回的过滤列表应该是:

[
  {
    "id": "g1",
    "group": "1",
    "heroes": [
      {
        "id": "g1h1",
        "hero": "hero1",
        "powers": [
          {
            "id": "g1h1p1",
            "power": "light",
            "strengths": [
              {
                "id": "g1h1p1s1",
                "strength": "guidence"
              }
            ]
          }
        ]
      }
    ]
  },
  {
  "id": "g2",
  "group": "2",
  "heroes": [
      {
        "id": "g2h1",
        "hero": "hero1",
        "powers": [
            {
              "id": "g2h1p1",
              "power": "electromancy",
              "strengths": [
                  {
                    "id": "g2h1p1s1",
                    "strength": "metal armor"
                  }
                ]
            }
          ]
      }
    ]
  }
]
我尝试了很多次,但都没有得到正确的结果。下面是我的一个尝试。我做错了什么?还是有更好的方法

  filterGroups()
  {
    //Iterate groups
    this.groups.forEach(group => {

      //remove empty groups
      if(group.heroes.length === 0)
      {
        let groupIndex: number = this.groups.findIndex(x => x.id === group.id);
        this.groups.splice(groupIndex, 1);
      }
      else {
        group.heroes.forEach(hero => {
          //remove heroes with no powers
          if(hero.powers.length === 0)
          {
            let heroIndex: number = group.heroes.findIndex(h => h.id === hero.id);
            group.heroes.splice(heroIndex, 1);
          }
          else {
            hero.powers.forEach(power => {
              //remove powers with no strengths
              if(power.strengths.length === 0)
              {
                let powerIndex: number = hero.powers.findIndex(p => p.id === power.id);
                hero.powers.splice(powerIndex,1);
              }            
              else {
                power.strengths.forEach(strength => {
                    if(this.selectedStrengths.some(x => x === strength.id))
                    {
                      let strengthIndex: number = power.strengths.findIndex(s => s.id === strength.id);
                      if(strengthIndex>-1)
                      {
                        power.strengths.splice(strengthIndex,1);
                      }
                    }              
                })

                //check if power is empty after filtering strengths
                if(power.strengths.length === 0)
                {
                  let powerIndex: number = hero.powers.findIndex(p => p.id === power.id);
                  hero.powers.splice(powerIndex,1);
                }
              }
            });

            //Check hero is empty after filtering powers
            if(hero.powers.length === 0)
            {
              let heroIndex: number = group.heroes.findIndex(h => h.id === hero.id);
              group.heroes.splice(heroIndex, 1);
            }
          }
        });

        //Check if group  is empty after filtering heroes
        if(group.heroes.length === 0)
        {
          let groupIndex: number = this.groups.findIndex(x => x.id === group.id);
          this.groups.splice(groupIndex, 1);
        }
      }
    });
  }

您正在
group.heros.forEach
中操作
group.heros
(通过
.splice
)这可能是问题的一部分。嗯,我明白了。有没有关于这种过滤的正确行动方案的想法过滤器很有意义,因为第35行
power.strength.splice(StrengtHindex,1)有一个拼写错误应为<代码>功率.强度.拼接(强度Hindex,1)
编辑了问题,因为它与键入脚本无关。您正在
group.heroes
(通过
.splice
)中操作
group.heroes.forEach
,这可能是问题的一部分。嗯,我明白了。有没有关于这种过滤的正确行动方案的想法过滤器很有意义,因为第35行
power.strength.splice(StrengtHindex,1)有一个拼写错误应为<代码>功率.强度.拼接(强度Hindex,1)编辑了该问题,因为它不需要输入脚本
    filterGroups() {
        return this.groups.filter(g => {
            g.heroes = g.heroes.filter(h => {
                h.powers = h.powers.filter(p => {
                    p.strengths = p.strengths.filter(s => this.selectedStrengths.indexOf(s.id) === -1);
                    return p.strengths.length > 0
                })
                return h.powers.length > 0;
            })
            return g.heroes.length > 0
        })
    }