【问题标题】:JavaScript, what is the fastest way to find n+ elements of array A in array B that are in the same order [closed]JavaScript,在数组B中以相同顺序查找数组A的n+个元素的最快方法是什么[关闭]
【发布时间】:2020-09-01 19:37:21
【问题描述】:

两个数组,每个包含 10 个元素:

A = [{a:1}, {a:2}, {a:3}, {a:4}, {a:5}, {a:6}, {a:7}, {a:8}, {a:9}, {a:10}]
B = [{a:11}, {a:221}, {a:4}, {a:5}, {a:6}, {a:7}, {a:8}, {a:10}, {a:9}, {a:33}]

在数组 A 中查找数组 B 中的 5+ 个元素并且顺序相同的最有效方法是什么?

预期结果:
{a:4, match:true}, {a:5, match:true}, {a:6, match:true}, {a:7, match:true}, {a:8, match:true}

【问题讨论】:

  • 你的方法是什么?
  • 让您知道A[3] === B[2] // false
  • @evolutionxbox 他​​们不相等,但我不确定你的意思是什么......
  • 所以当你比较值时你是知道的。这是一个有效的观点
  • 它们需要连续吗? IE。在上面的数组中,算法会找到 5 个还是 6 个匹配的元素?

标签: javascript arrays performance compare comparison


【解决方案1】:

这种方法会为属性 a 寻找相同的值,并假设仅存在一个相同有序对象的子集。

您可以使用两个循环,一个用于存储所有索引,一个用于获取索引并与存储的索引进行检查的过滤器函数。

const
    a = [{ a: 1 }, { a: 2 }, { a: 3 }, { a: 4 }, { a: 5 }, { a: 6 }, { a: 7 }, { a: 8 }, { a: 9 }, { a: 10 }],
    b = [{ a: 11 }, { a: 221 }, { a: 4 }, { a: 5 }, { a: 6 }, { a: 7 }, { a: 8 }, { a: 10 }, { a: 9 }, { a: 33 }],
    result = b.filter(
        ((indices, i, last) => ({ a }, j, { [j - 1]: { a: last } = {} }) => {
            if (!i && (a in indices)) return i = indices[a] + 1;
            if (indices[a] === i && indices[last] + 1 === i) return i++;
        })
        (Object.fromEntries(a.map(({ a }, i) => [a, i])), 0)
    );

console.log(result);
.as-console-wrapper { max-height: 100% !important; top: 0; }

【讨论】:

  • 您的解决方案返回 6 个元素,最后一个 {a:10} 不匹配。算法只应返回五个元素:d.pr/i/yu8b3C
  • 这很好!如何标记返回的元素,即match:true?
  • 过滤后(只进行更新)?哪个数组?
  • 那行得通,但我想知道有没有办法在结果中标记元素而不需要额外的迭代,所以性能不会下降。
  • 如果两个数组的第一个元素匹配,则此算法失败:a[0] = 1, b[0] = 1 - 结果仅包含第一个元素。如何改进这一点,使算法返回预期的结果(有问题描述)?
【解决方案2】:

如果有人需要,这就是我带来的。这并不完美 - 在某些情况下,当少于 5 个元素匹配并且它们被放置在 A 表的末尾时,结果会返回它们。但在这种情况下,结果可以在算法之外被忽略。

const a = [{a:1}, {a:2}, {a:3}, {a:4}, {a:5}, {a:6}, {a:7}, {a:8}, {a:9}, {a:10}]
const b = [{a:11}, {a:221}, {a:4}, {a:5}, {a:6}, {a:7}, {a:8}, {a:10}, {a:9}, {a:33}]

    let j = 0;
    let firstIndex;
    let minMatch = 5

    while(j <= b.length && b.length) {
      if(j === 0) {
        firstIndex = a.map(({a}) => a).indexOf(b[j].a);
        if(firstIndex > -1) {
          j++
        } else {
          b.shift();
        }
      } else {
        if (b[j].a === a[j + firstIndex].a) {
          j++;
        } else {
          if (j < minMatch) {
            while(j > 0) {
              b.shift();
              j--;
            }
            firstIndex = a.map(({a}) => a).indexOf(b[j].a);
            if (firstIndex > -1) {
              j++
            }
          } else {
            while (b.length > j) {
              b.pop();
            }
            break;
          }
        }
      }
    }
    console.log(b);
    

【讨论】:

    猜你喜欢
    • 2012-05-07
    • 1970-01-01
    • 2013-12-26
    • 2021-11-03
    • 2012-05-07
    • 1970-01-01
    • 1970-01-01
    • 2020-05-26
    • 2021-11-03
    相关资源
    最近更新 更多