首页 > 解决方案 > 提高嵌套 for 循环的速度

问题描述

我目前正在尝试解决工作问题,所以很抱歉代码必须有点模糊,但这个概念很简单,我应该能够在不具体的情况下传达我的问题。

最终目标是取两个变量(X,Y),我需要对每个 Y 运行 X。我提供的样本数据(甚至没有一半)是 X = 107 和 Y = 6400,所以我们'仅针对示例数据重新查看 684,800 次迭代。这显然需要一段时间,但我想尽我所能缩短时间。

我尝试了两种不同的方法,一种是嵌套 for 循环,一种是我尝试并行运行它,但老实说,我对并行性没有太多经验,所以我知道为什么它不起作用。在我遇到与手头问题无关的错误之前,这两种情况都运行了相同的时间(3.5 小时)

我尝试了几种使用 ParameterizedTest 在两个 CSV 中加载的不同方法,但我无法开始工作,所以如果有一种使用 JUnit 的简单方法,我很乐意听到它。我目前正在使用 JUnit 5.3.1。

尝试1:

@Test
void test() {
    List<String> varX = loadCsv(path);
    List<String> varY = loadCsv(otherPath);

    for (String x : varX) {
        for (String y : varY) {
            // Do the work
        }
    }
}

尝试2:

@Test
void test() {
    List<String> varX = loadCsv(path);
    List<String> varY = loadCsv(otherPath);

    varX.parallelStream().forEach(x -> {
        for (String x : varX) {
            for (String y : varY) {
                // Do the work
            }
        }
    }
}

标签: javajunit

解决方案


关于使用 a @ParameterizedTest- 您可以同时加载 CSV,将它们映射到 aStream<Arguments>并参数化测试方法以使用它们:

public static Stream<Arguments> loadTestData() {
    List<String> varX = loadCsv(path);
    List<String> varY = loadCsv(otherPath);

    return varX.parallelStream()
               .flatMap(x -> varY.parallelStream().map(y -> Arguments.of(x, y)));
}

@ParameterizedTest
@MethodSource("loadTestData")
void test(String x, String y) {
    // You now have a combination of x and y:
    // test that the logic under test works for that combination
}

推荐阅读