首页 > 解决方案 > 根据字符串过滤嵌套的对象数组

问题描述

大家好,我有这个对象数组:

const example = {
    sections: [
        {
            id: 'something',
            sectionHeader: 'Something',
            content: [
                {
                    contentId: 'something1',
                    contentHeader: 'Lorem ipsum',
                },
                {
                    contentId: 'something2',
                    contentHeader: 'Lorem ipsum',
                },
            ],
        },
        {
            id: 'international',
            sectionHeader: 'International',
            content: [
                {
                    contentId: 'international1',
                    contentHeader: 'Mauris tempus vestibulum',
                },
            ],
        },
        {
            sectionId: 'home',
            sectionHeader: 'Home',
            content: [
                {
                    contentId: 'home1',
                    contentHeader: 'Etiam volutpat rhoncus',
                },
                {
                    contentId: 'home2',
                    contentHeader: 'Curabitur searchedValue mi lectus',
                },
                {
                    contentId: 'home3',
                    contentHeader: 'Orci varius natoque',
                },
            ],
        },
        {
            sectionId: 'city',
            sectionHeader: 'City',
            content: [
                {
                    contentId: 'city1',
                    contentHeader: 'Aliquam cursus',
                },
            ],
        },
    ],
};

我想根据sectionHeadercontentHeader中的“搜索值”获得一个新的过滤数组:

const searchValue = 'searchedValue';

const filteredResults = example.sections.filter((section) => section.sectionHeader.toLowerCase().trim().includes(searchValue)
    || section.content.some((content) => content.contentHeader.toLowerCase().trim().includes(searchValue)))
    .filter((section) => section.content.length);

结果是包含所有三个内容对象(在本例中为“home1”、“home2”和“home3”)的部分。预期结果只是包含搜索值('home2')的对象:

{
    sectionId: 'home',
    sectionHeader: 'Home',
    content: [
        {
            contentId: 'home2',
            contentHeader: 'Curabitur searchedValue mi lectus',
        },
    ],
},

非常感谢您的帮助。

标签: javascriptarraysjavascript-objects

解决方案


我写了一个快速函数,它可以帮助解释每一步,希望能让你走上正确的道路。它是这样写的,以便我可以更轻松地解释每个步骤。

脚步:

  • 我创建了一个接受搜索条件的函数。
  • 创建了所有节标题的地图
  • 创建了所有部分内容标题的地图
  • 遍历每个节标题并查看它是否与搜索条件匹配
  • 如果是,则返回整个部分
  • 如果不是,我们将遍历内容标题并查看是否有任何值符合我们的搜索条件
  • 如果它确实存储,这些索引在一个数组中
  • 返回部分并使用数组过滤器覆盖内容键,该过滤器保留搜索条件返回 true 的所有索引
  • 返回结果

如果你想减少代码的行数,我在下面写了一个更现代的版本

const example = {
  sections: [
    {
      id: "something",
      sectionHeader: "Something",
      content: [
        {
          contentId: "something1",
          contentHeader: "Lorem ipsum"
        },
        {
          contentId: "something2",
          contentHeader: "Lorem ipsum"
        }
      ]
    },
    {
      id: "international",
      sectionHeader: "International",
      content: [
        {
          contentId: "international1",
          contentHeader: "Mauris tempus vestibulum"
        }
      ]
    },
    {
      sectionId: "home",
      sectionHeader: "Home",
      content: [
        {
          contentId: "home1",
          contentHeader: "Etiam volutpat rhoncus"
        },
        {
          contentId: "home2",
          contentHeader: "Curabitur searchedValue mi lectus"
        },
        {
          contentId: "home3",
          contentHeader: "Orci varius natoque"
        }
      ]
    },
    {
      sectionId: "city",
      sectionHeader: "City",
      content: [
        {
          contentId: "city1",
          contentHeader: "Aliquam cursus"
        }
      ]
    }
  ]
};

function search(value) {
  const results = [];
  const sectionHeaders = example.sections.map(section => section.sectionHeader);
  const contentHeaders = example.sections.map(section =>
    section.content.map(content => content.contentHeader)
  );

  example.sections.forEach((_section, index) => {
    const foundIndexes = [];

    if (sectionHeaders[index] === value) {
      return results.push(example.sections[index]);
    }

    contentHeaders[index].forEach((header, index) => {
      if (header.includes(value)) {
        foundIndexes.push(index);
      }
    });

    if (foundIndexes.length !== 0) {
      return results.push({
        ...example.sections[index],
        content: example.sections[index].content.filter((_content, index) =>
          foundIndexes.includes(index)
        )
      });
    }
  });

  return results.length === 0 ? "No results found" : results;
}

console.log(search("searchedValue"));

const example = {
  sections: [
    {
      id: "something",
      sectionHeader: "Something",
      content: [
        {
          contentId: "something1",
          contentHeader: "Lorem ipsum"
        },
        {
          contentId: "something2",
          contentHeader: "Lorem ipsum"
        }
      ]
    },
    {
      id: "international",
      sectionHeader: "International",
      content: [
        {
          contentId: "international1",
          contentHeader: "Mauris tempus vestibulum"
        }
      ]
    },
    {
      sectionId: "home",
      sectionHeader: "Home",
      content: [
        {
          contentId: "home1",
          contentHeader: "Etiam volutpat rhoncus"
        },
        {
          contentId: "home2",
          contentHeader: "Curabitur searchedValue mi lectus"
        },
        {
          contentId: "home3",
          contentHeader: "Orci varius natoque"
        }
      ]
    },
    {
      sectionId: "city",
      sectionHeader: "City",
      content: [
        {
          contentId: "city1",
          contentHeader: "Aliquam cursus"
        }
      ]
    }
  ]
};

function search(value) {
  const results = example.sections
    .map(section => {
      if (section.sectionHeader === value) {
        return section;
      }

      if (
        section.content.some(section => section.contentHeader.includes(value))
      ) {
        return {
          ...section,
          content: section.content.filter(content =>
            content.contentHeader.includes(value)
          )
        };
      }

      return false;
    })
    .filter(Boolean);

  return results.length === 0 ? "No results found" : results;
}

console.log(search("searchedValue"));


推荐阅读