简体   繁体   English

Nodejs 使用 async/bluebird 跳出循环?

[英]Nodejs break out of loop with async/bluebird?

So, I've got the following code that works, but I'd like for it to not use a for-loop anymore.所以,我有以下有效的代码,但我希望它不再使用 for 循环。

The important bit is the "break" story.重要的一点是“休息”的故事。

    for (const obj of objects) {
        let found = false;

        for (const item of items) {
            const result = item.get(obj);
            if (typeof result !== 'undefined') {
                found = true;
                break;
            }
        }

        if (!found) {
            notDefined.push(obj);
        }
    }

I've tried it with Bluebird but I'm failing there.我已经用 Bluebird 试过了,但我在那里失败了。 Array.prototype.forEach isn't an option, it cannot be stopped. Array.prototype.forEach 不是一个选项,它无法停止。

What else can I try?我还能尝试什么?

EDIT: The point is filling that list of objects, the "notDefined" one.编辑:重点是填充对象列表,即“notDefined”列表。 The list represents items not found in a map that has been filled purposefully.该列表表示在有意填充的地图中找不到的项目。

So a bunch of them are tested for a match.所以他们中的一堆人接受了匹配测试。

If the item does get found, we should skip to the next group.如果确实找到了该项目,我们应该跳到下一组。 And of course: stop looping over the items because we've found a match and so there's no point in continuing.当然:停止循环遍历项目,因为我们找到了匹配项,因此没有继续下去的意义。 No need to keep checking all the remaining items, which may well be several hundred thousands.没有必要继续检查所有剩余的项目,很可能有几十万。

EDIT2: The purpose of that "notDefined" list is to write the objects to a text file, that can later be checked manually. EDIT2:“notDefined”列表的目的是将对象写入文本文件,稍后可以手动检查。

The variable names have been changed away from their originals, as to have something different on here.变量名称已从其原始名称中更改,因此此处有所不同。

The purpose of the code is comparing the contents of several directories on one machine, to the content on several directories on an other machine.该代码的目的是将一台机器上的多个目录的内容与另一台机器上的多个目录的内容进行比较。

This data comes in as several CSV files.此数据以多个 CSV 文件的形式出现。 They are all read and a list is generated per CSV file.它们都被读取,并为每个 CSV 文件生成一个列表。 The data in this CSV file is:此 CSV 文件中的数据为:

  • Absolute file path绝对文件路径
  • File size文件大小
  • Md5 MD5

And some other metadata.以及其他一些元数据。

However, this list each time does not contain merely the strings of the absolute file path, it contains a Map() , the key being a combination of the 3 mentioned pieces of data, just above.然而,这个列表每次不仅仅包含绝对文件路径的字符串,它包含一个Map() ,键是上面提到的 3 条数据的组合。

So we have several CSV files for machine A, and then several CSVs for machine B. And we wish to see if items found on machine A, can also be found on machine B.所以我们有机器 A 的几个 CSV 文件,然后机器 B 有几个 CSV 文件。我们希望看看在机器 A 上找到的项目是否也可以在机器 B 上找到。

That's what I'm trying to do here: loop over all the CSVs and find matching items.这就是我在这里要做的:遍历所有 CSV 并找到匹配的项目。

If I find a match, then there's no point to continue checking and I can skip to the next set.如果我找到匹配项,则没有必要继续检查,我可以跳到下一组。 That's where the break;这就是break;的地方break; comes from.来自。

But I do need to check for every single match and then write a result for all items not found anywhere.但是我确实需要检查每个匹配项,然后为在任何地方找不到的所有项目写一个结果。

It looks to me like you have two Arrays, objects and items .在我看来,你有两个 Arrays, objectsitems

And, it looks to me like you want a decently-performing way to know whether each object is missing from all your Maps.而且,在我看来,您想要一种性能良好的方式来了解所有地图中是否缺少每个对象。 I guess your interest in breaking out of a for-loop is part of your strategy to make this perform decently.我想您对打破 for 循环的兴趣是您使其表现良好的策略的一部分。

May I suggest another approach?我可以建议另一种方法吗? Let's start by making a single Set of all the keys in all your Map objects.让我们从创建所有 Map 对象中的所有键的单个 Set 开始。 Something like this.像这样的东西。

const allKeys = new Set()
for (const item of items)
  for (const key of item.keys())
    allKeys.add(key)

Now you run through your array of objects, one by one, and push them into notDefined if they're absent from the allKeys set.现在,您一个接一个地运行对象数组,如果它们不在allKeys集中,则将它们推入notDefined

for (const obj of objects)
  if (!allKeys.has(obj)) 
    notDefined.push(obj)

This gets you out of nested iterations on two arrays.这让您摆脱了两个数组的嵌套迭代。 And it performs well because Set lookups are fast.它表现良好,因为 Set 查找速度很快。

All together, in some perfectly synchronous tight loops (no Promises needed):总之,在一些完美同步的紧密循环中(不需要承诺):

const allKeys = new Set()
for (const item of items)
  for (const key of item.keys())
    allKeys.add(key)

for (const obj of objects)
  if (!allKeys.has(obj))
     notDefined.push(obj)

To make it even faster, you could consider building your allKeys set as you read your raw data from your CSV files.为了使其更快,您可以考虑在从 CSV 文件读取原始数据时构建allKeys集。 That would save the pass over all the elements of items .这将节省对items所有元素的传递。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM