根据对象数组的值筛选对象



我正在React中制作一个笔记应用程序,我有一些数据看起来像这样。我想对它进行过滤,以便只保留数组中包含标记的对象,而删除其余对象。

原始数据

const obj = {
Mon: [
{ id: 1, content: 'Some text', tag: 'home' },
{ id: 2, content: 'Some text', tag: 'work' },
{ id: 3, content: 'Some text', tag: 'project' },
],
Tue: [
{ id: 4, content: 'Some text', tag: 'project' },
{ id: 5, content: 'Some text', tag: 'moving' },
],
Wed: [
{ id: 6, content: 'Some text', tag: 'home' },
{ id: 7, content: 'Some text', tag: 'home' },
{ id: 8, content: 'Some text', tag: 'work' },
],
};

过滤后的所需数据";家;以及";工作

用作筛选术语的数组

const filterTags = ['home', 'work']

我们剩下的数据

{
Mon: [
{ id: 1, content: 'Some text', tag: 'home' },
{ id: 2, content: 'Some text', tag: 'work' },
],
Wed: [
{ id: 6, content: 'Some text', tag: 'home' },
{ id: 7, content: 'Some text', tag: 'home' },
{ id: 8, content: 'Some text', tag: 'work' },
],
};

想要使用数组进行筛选的原因是,我希望用户能够点击他们想要查看的笔记的标签(这些标签当前存储在useState()中)。

对于过滤后的剩余数据,我计划通过它进行映射,并呈现如下相关元素:

<>
{Object.entries(sortedNotesData).map(
([noteDate, noteContent], i) => (
<div key={i}>
<NoteDate noteDate={noteDate} />
<div className="column">
{noteContent
.map((note) => (
<>
<NoteCard
key={note.id}
id={note.id}
content={note.content}
tag={note.tag}
/>
</>
))}
</div>
</div>
)
)}
</>

任何关于过滤原始数据的最佳实践方法的建议都将是非常棒的,包括是否最好在render()之外的函数中处理数据过滤,或者是否可以在.map()之前内联完成。

  • 使用object.entries.将对象转换为数组

  • 映射嵌套数组并使用filterTags数组过滤值。

  • 删除其中没有匹配项目的天数。

  • 最后使用object.fromEntries 将嵌套数组转换回对象

const obj = {
Mon: [
{ id: 1, content: "Some text", tag: "home" },
{ id: 2, content: "Some text", tag: "work" },
{ id: 3, content: "Some text", tag: "project" },
],
Tue: [
{ id: 4, content: "Some text", tag: "project" },
{ id: 5, content: "Some text", tag: "moving" },
],
Wed: [
{ id: 6, content: "Some text", tag: "home" },
{ id: 7, content: "Some text", tag: "home" },
{ id: 8, content: "Some text", tag: "work" },
],
},
filterTags = ["home", "work"],
filteredObj = Object.fromEntries(
Object.entries(obj)
.map(([key, value]) => [
key,
value.filter(({ tag }) => filterTags.includes(tag)),
])
.filter(([, value]) => value.length)
);
console.log(filteredObj);

您还可以通过删除最后一个筛选器来保留没有匹配项目的天数。

const obj = {
Mon: [
{ id: 1, content: "Some text", tag: "home" },
{ id: 2, content: "Some text", tag: "work" },
{ id: 3, content: "Some text", tag: "project" },
],
Tue: [
{ id: 4, content: "Some text", tag: "project" },
{ id: 5, content: "Some text", tag: "moving" },
],
Wed: [
{ id: 6, content: "Some text", tag: "home" },
{ id: 7, content: "Some text", tag: "home" },
{ id: 8, content: "Some text", tag: "work" },
],
},
filterTags = ["home", "work"],
filteredObj = Object.fromEntries(
Object.entries(obj).map(([key, value]) => [
key,
value.filter(({ tag }) => filterTags.includes(tag)),
])
);
console.log(filteredObj);

类似于SSM的答案,但如果您不希望包括没有结果的天数,则

  • 使用object.entries将对象转换为数组
  • 使用filterTags上的includes筛选内容
  • 仅添加具有筛选结果的日期返回1个或多个结果

const obj = {
Mon: [
{ id: 1, content: 'Some text', tag: 'home' },
{ id: 2, content: 'Some text', tag: 'work' },
{ id: 3, content: 'Some text', tag: 'project' },
],
Tue: [
{ id: 4, content: 'Some text', tag: 'project' },
{ id: 5, content: 'Some text', tag: 'moving' },
],
Wed: [
{ id: 6, content: 'Some text', tag: 'home' },
{ id: 7, content: 'Some text', tag: 'home' },
{ id: 8, content: 'Some text', tag: 'work' },
],
};

const filterTags = ['home', 'work']
//this will hold an object of results
let filteredResults = {};

Object.entries(obj).forEach(day => {
const name = day[0];
const filtered = day[1].filter(content => filterTags.includes(content.tag))
if (filtered.length > 0) {
filteredResults[name] = filtered
}
})

console.log(filteredResults)

最新更新