从对象数组中过滤重复项

Filtering duplicates form array of objects

寻找以下代码无法正确过滤的原因的解释。我有一个对象数组,其中一个属性是 buy_mth_yr,其格式如下 mmm-yy。

buy_mth_yr : 'Apr-18'

我正在尝试获取所有唯一 buy_mth_yr 值的列表和 return 作为标签值对象的列表,以传递到过滤器中。我已经在一个单独的堆栈溢出问题中找到了解决方案,我问这个问题的目的更多是为了理解为什么我下面的原始解决方案不起作用。所以可以说 data 是我的带有 buy_mth_yr 键的对象列表。 if 语句每次都调用,我最终得到一个未过滤的列表。任何 help/insight 感谢!

let distinct = [];
    data.forEach(record =>{
        let temp = {label: record.buy_mth_yr, value: record.buy_mth_yr}
        if(!(temp in distinct)){
            distinct.push(temp)
        }
    })   
    return distinct;

to understand why my original solution below doesn't work

因为您正在进行参考比较 - 第一个 link 在 google 上弹出,它可能会有所帮助:https://dmitripavlutin.com/how-to-compare-objects-in-javascript/#1-referential-equality

({a:1}) !== ({a:1})

// but
const obj = {a:1};
obj === obj

temp 永远不会 distinct 中,因为它每次都是一个新对象。

编辑:

除此之外,更好的解决方案(有上千种写法,下面只是一个示例)如下所示:

const isShallowEqualWith = (a) => (b) => {
  const keysA = Object.keys(a);
  const keysB = Object.keys(b);
  return keysA.length === keysB.length && keysA.every(k => a[k] === b[k]);
}

let distinct = [];
    data.forEach(record =>{
        let temp = {label: record.buy_mth_yr, value: record.buy_mth_yr}
        if(!distinct.find(isShallowEqualWith(temp)) {
          distinct.push(temp);
        }
    })   
    return distinct;

我认为您的 !(temp in distinct) 不是您想做的检查:改用 !distinct.includes(temp)

但是你应该看看带有 _.uniq_.uniqBy 函数的 lodash 库:https://www.geeksforgeeks.org/lodash-_-uniqby-method/