javascript - 根据字符串过滤嵌套的对象数组
问题描述
大家好,我有这个对象数组:
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',
},
],
},
],
};
我想根据sectionHeader或contentHeader中的“搜索值”获得一个新的过滤数组:
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',
},
],
},
非常感谢您的帮助。
解决方案
我写了一个快速函数,它可以帮助解释每一步,希望能让你走上正确的道路。它是这样写的,以便我可以更轻松地解释每个步骤。
脚步:
- 我创建了一个接受搜索条件的函数。
- 创建了所有节标题的地图
- 创建了所有部分内容标题的地图
- 遍历每个节标题并查看它是否与搜索条件匹配
- 如果是,则返回整个部分
- 如果不是,我们将遍历内容标题并查看是否有任何值符合我们的搜索条件
- 如果它确实存储,这些索引在一个数组中
- 返回部分并使用数组过滤器覆盖内容键,该过滤器保留搜索条件返回 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"));
推荐阅读
- javascript - 为什么画布上的矩形会移位?
- maven - 如何将 Cytoscape 画布集成到 JavaFX Maven 应用程序中?
- paypal - Silvestripe 4.4 无法安装omnipay/paypal
- android - 在每台 Android 设备上显示相同大小的文本
- android - 使用 Mockk 模拟语言环境
- entity-framework - 我们可以通过实体框架中的查询执行时间来动态设置命令超时吗?
- coldfusion - 内存文件系统限制不能超过 JVM 最大堆大小
- java - 用我的函数模拟 MissingMethodInvocationException
- command-line - Rust 如何处理进程参数?
- c - 当我按下按钮时,如何对 nRF52 DK 进行编程以发送 BLE MIDI 消息?