使用对象过滤对象数组位于嵌套数组属性中

时间:2019-10-22 09:28:51

标签: javascript arrays typescript

我有以下用例

我有

  • 包含courses列表的对象的数组
  • 包含students和嵌套array: studies的对象数组

我需要找到任何学生都没有学过的课程。

如何实现?

以下为代码正则。

let courses = [
    { id: 'A' },
    { id: 'B' },
    { id: 'C' },
    { id: 'D' }, <-- not studied by any one
    { id: 'E' },
    { id: 'F' }, <-- not studied by any one
];

let students = [
    {
        name: 'STD1',
        study: [
            { id: 'A' },
            { id: 'C' }
        ]
    },
    {
        name: 'STD2',
        study: [
            { id: 'B' },
            { id: 'E' }
        ]
    }

];

预期输出

  const notUsedCourse = [{ id: 'D' }, { id: 'F' }];

3 个答案:

答案 0 :(得分:1)

您可以将id研究过的课程students保存到Set中,以便我们以后检查课程是否被学习。 与filtersome组合使用的解决方案相比,其优势在于,当coursesstudents的大小变大时,此解决方案将更快,因为前者具有时间复杂性的O(n^3)

const courses = [
    { id: 'A' },
    { id: 'B' },
    { id: 'C' },
    { id: 'D' },
    { id: 'E' },
    { id: 'F' },
];

const students = [
    {
        name: 'STD1',
        study: [
            { id: 'A' },
            { id: 'C' }
        ]
    },
    {
        name: 'STD2',
        study: [
            { id: 'B' },
            { id: 'E' }
        ]
    }

];

const usedCourseIds = new Set(students.flatMap(student => student.study).map(course => course.id));
const notUsedCourses = courses.filter(course => !usedCourseIds.has(course.id));

console.log(notUsedCourses);

答案 1 :(得分:0)

您可以将.filter.some结合使用,以遍历并搜索学生是否有课程:

let courses = [
    { id: 'A' },
    { id: 'B' },
    { id: 'C' },
    { id: 'D' },
    { id: 'E' },
    { id: 'F' },
];

let students = [
    {
        name: 'STD1',
        study: [
            { id: 'A' },
            { id: 'C' }
        ]
    },
    {
        name: 'STD2',
        study: [
            { id: 'B' },
            { id: 'E' }
        ]
    }

];

let notUsedCourse = courses.filter(
  course => !students.some(
    student => student.study.some(
      study => study.id === course.id
    )
  )
);

console.log(notUsedCourse);

答案 2 :(得分:0)

您可以先获取所访问的课程,然后过滤所有课程。

var courses = [{ id: 'A' }, { id: 'B' }, { id: 'C' }, { id: 'D' }, { id: 'E' }, { id: 'F' }],
    students = [{ name: 'STD1', study: [{ id: 'A' }, { id: 'C' }] }, { name: 'STD2', study: [{ id: 'B' }, { id: 'E' }] }],
    seen = students.reduce(
        (seen, { study }) => study.reduce((s, { id }) => s.add(id), seen),
        new Set
    ),
    missing = courses.filter(({ id }) => !seen.has(id));

console.log(missing)