【问题标题】:How to .filter an array against an array with .includes?如何使用 .includes 针对数组过滤数组?
【发布时间】:2020-01-04 22:41:54
【问题描述】:

我查看了许多其他帖子,但无法解决我的问题。

我正在开发一个音乐/和弦播放程序,我想过滤掉所有包含一个或多个音符(我的程序中的数字)的和弦(又名对象),这些音符是失调的。

我有一个名为 chordLibrary 的数组,其中填充了对象(例如,{notesInChord: [5, 8], chordName: 'Major'})。我有另一个带有数字的数组(outOfKeyNotes = [11, 12];)。我想 .filter 并仅返回 chordLibrary 中不包括元素 notesInChordoutOfKeyNotes 中的数字的对象。

例如:

// THIS is the original array:
const chordLibrary = [ 
    { notesInChord: [5, 8], chordName: 'Major' },
    { notesInChord: [5, 8, 11], chordName: 'Dominant 7th' },
    { notesInChord: [4, 8, 12], chordName: 'Minor Major 7th' }
];

// THIS is what I hope to end up with after filtering for the array [11,12]:
let chordsInKey = [ 
    { notesInChord: [5, 8], chordName: 'Major' },
];

这是我目前无法运行的程序。它只是返回整个原始数组。

const chordLibrary = [ 
    { notesInChord: [5, 8], chordName: 'Major' },
    { notesInChord: [5, 8, 11], chordName: 'Dominant 7th' },
    { notesInChord: [4, 8, 12], chordName: 'Minor Major 7th' }
];

let outOfKeyNotes = [11, 12];

console.log(chordLibrary.length);

let chordsInKey = chordLibrary.filter(function(item) {
    return !outOfKeyNotes.includes(item.notesInChord);
});

console.log(chordsInKey);
console.log(chordsInKey.length);

如果我更改程序以使chordLibrary 只是一个数值数组而不是对象数组,它就可以正常工作。它只是不适合我的需要。这是一个工作示例:

let chordLibrary = [1,2,3,11,12];
let outOfKeyNotes = [11, 12];

console.log(chordLibrary.length);

let chordsInKey = chordLibrary.filter(function(item) {
    return !outOfKeyNotes.includes(item);
});

console.log(chordsInKey);
console.log(chordsInKey.length);

我错过了什么?谢谢

【问题讨论】:

    标签: javascript arrays filter return


    【解决方案1】:

    您可以使用Array#some() 来检查outOfKeyNotes 中是否存在任何notesInChord

    const chordLibrary = [ 
        { notesInChord: [5, 8], chordName: 'Major' },
        { notesInChord: [5, 8, 11], chordName: 'Dominant 7th' },
        { notesInChord: [4, 8, 12], chordName: 'Minor Major 7th' }
    ];
    
    let outOfKeyNotes = [11, 12];
    
    let chordsInKey = chordLibrary.filter(function(item) {
        return !item.notesInChord.some(function(v){
             return outOfKeyNotes.includes(v);
        });
    });
    
    console.log(chordsInKey);

    【讨论】:

    • 我了解到 .some 通常会返回包含存在值之一的任何元素。但是,这里它只返回一个不包括 outOfKeyNotes 的和弦。我假设使用“!”让它这样工作吗? @TalKoren 的答案似乎是一个更简洁的版本,但它们的工作方式相同,是吗?
    • 正确。 some() 返回一个布尔值,你想否定它(使用!),因为你不想包含任何东西
    • 另一个不太干净...我也可以使用箭头函数编写它,但将其保留为 es5 函数语法以与您编写代码的方式保持一致。请注意,some() 会在遇到匹配时立即中断,而 every() 必须遍历整个数组。在小数组上它并不重要......在大数据集上可以有所作为
    • 啊,很有趣。非常感谢您的澄清。我也很高兴使用 .some。非常有用。
    【解决方案2】:

    您正在尝试使用includes 来查看一个值数组是否包含另一个值数组。

    相反,您可以在过滤机制中使用Array.every,这可以确保数组中的每个元素都通过特定的测试。

    我会改变

    return !outOfKeyNotes.includes(item.notesInChord);
    

    return item.notesInChord.every(note => !outOfKeyNotes.includes(note));
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-07-08
      • 2015-10-21
      • 2023-01-02
      • 2021-10-21
      • 2022-10-14
      • 1970-01-01
      相关资源
      最近更新 更多