首页 > 解决方案 > 检查数组是否包含一些对象

问题描述

如下图,如果想查询testArray中的某个对象是否在currentArray中,可以使用for循环遍历数组,也可以使用find(),,, . 最糟糕的表现是如果我全部陷入至少一次O(n ^ 2)。some()include()

如果我首先过滤 currentArray 中余额不是 999 或 999.999 的项目,然后检查 testArray。性能是否优于至少一次?或者有什么方法可以做得更好?

谢谢!

let currentArray = [
  {account: 1, balance: 200},
  {account: 2, balance: 100},
  {account: 3, balance: 300},
  {account: 4, balance: 999},
  {account: 5, balance: 999.999},
  {account: 6, balance: 999},
  {account: 15, balance: 999.999},
  {account: 8, balance: 100},
  {account: 9, balance: 300},
  {account: 10, balance: 300},
]

let testArray = [
  {account: 4, balance: 999},
  {account: 5, balance: 999.999},
  {account: 6, balance: 999},
  {account: 7, balance: 999.999},
  {account: 8, balance: 999},
  {account: 9, balance: 999.999},
  {account: 10, balance: 999},
  {account: 11, balance: 999.999},
  {account: 12, balance: 999},
  {account: 13, balance: 999.999},
  {account: 14, balance: 999},
  {account: 15, balance: 999.999},
]

标签: javascriptarraysalgorithmfor-loop

解决方案


据我了解,对于给定的示例数组,您期望以下结果:

[
    { "account":  4, "balance": 999     },
    { "account":  5, "balance": 999.999 },
    { "account":  6, "balance": 999     },
    { "account": 15, "balance": 999.999 }
]

...因为这些都出现在两个数组中。

为了以更好的时间复杂度实现这一点,请为每个对象使用唯一的键。知道您的对象有一个包含两个属性的键,您可以将这两个值组合在一个数组中并生成其 JSON 编码(或任何其他合适的编码):该字符串将是每个对象的唯一 id。将第一个数组的那些存储在一个集合中,然后迭代第二个数组以检查对象是否具有出现在集合中的此类标识符。

let currentArray = [
  {account: 1, balance: 200},
  {account: 2, balance: 100},
  {account: 3, balance: 300},
  {account: 4, balance: 999},
  {account: 5, balance: 999.999},
  {account: 6, balance: 999},
  {account: 15, balance: 999.999},
  {account: 8, balance: 100},
  {account: 9, balance: 300},
  {account: 10, balance: 300},
];

let testArray = [
  {account: 4, balance: 999},
  {account: 5, balance: 999.999},
  {account: 6, balance: 999},
  {account: 7, balance: 999.999},
  {account: 8, balance: 999},
  {account: 9, balance: 999.999},
  {account: 10, balance: 999},
  {account: 11, balance: 999.999},
  {account: 12, balance: 999},
  {account: 13, balance: 999.999},
  {account: 14, balance: 999},
  {account: 15, balance: 999.999},
];

const hash = ({account, balance}) => JSON.stringify([account, balance]);

let ref = new Set(currentArray.map(hash));
let result = testArray.filter(obj => ref.has(hash(obj)));
console.log(result);

如果您只对是否存在这样的对象感兴趣,请使用some代替filter. 返回值将是一个布尔值:当存在这样的对象时为 true,否则为 false。

如果您有兴趣找到一个这样的对象,请使用find而不是filter. 返回值将是第一个找到的对象,或者undefined没有这样的对象。

更好的时间复杂度的关键是使用Set. 它也可以是一个以 JSON 字符串作为属性名称的普通对象,每个对象都有一个任意值(如true)。


推荐阅读