java - 循环内的逻辑?或者更确切地说是两个独立的几乎相同的循环?

标签 java loops if-statement convention

注意:我的印象是您想避免循环内的逻辑语句。我认为之所以这样说,部分原因是编译器如何优化迭代行为可预测的任何循环。虽然我几乎可以肯定我以前听过这个,而且听了很长时间,但我一直认为这是一个惯例。遗憾的是我找不到任何好的引用资料。如果这是真的,但是由于“DRY”原则(不要重复自己),存在一些冲突的情况。

PRETEXT:假设您有一个相当大的数据集,比如我在本例中使用的多维数组。此外假设您需要遍历每个条目并对所有或部分元素执行某些操作,并且您需要能够选择要执行的一个或另一个操作。这需要制作两种方法,其中 90%-99% 的代码在两者之间是相同的,而只有运算符或方法调用不同。如果这是 C++,我会想提供一个指向循环函数的函数指针,尽管我不知道这是否也是最好避免的。

问题:使用逻辑语句并且只有一个循环还是两个几乎相同的方法更好?

示例:我提供了一些示例来说明“双胞胎”方法解决方案看起来有多么冗余:

// This method is provided for completeness of the example
// and to provide some clue as to what boolean parameter and logic statement 
// I could alternatively have implemented within the loop method instead of external to it.
public int[][] addOrSubtractArrays(int[][] a, int[][] b, boolean useAdd){
    if(a == null || b == null || a.length != b.length || a.length < 1 || a[0].length != b.length)
        return null;
    return useAdd ? add(a, b) : subtract(a, b);
}

private int[][] add(int[][] a, int[][] b){
    int h = a.length;
    int w = a[0].length;
    int[][] c = new int[h][w];
    for(int y = 0; y < h; y++){
        for(int x = 0; x < w; x++){
            c[y][x] = a[y][x] + b[y][x];
        }
    }
    return c;
}

private int[][] subtract(int[][] a, int[][] b){
    int h = a.length;
    int w = a[0].length;
    int[][] c = new int[h][w];
    for(int y = 0; y < h; y++){
        for(int x = 0; x < w; x++){
            c[y][x] = a[y][x] - b[y][x];
        }
    }
    return c;
}

示例 2:(显而易见的?)替代方案

private int[][] addOrSubtract(int[][] a, int[][] b, boolean useAdd){
    if(a == null || b == null || a.length != b.length || a.length < 1 || a[0].length != b.length)
        return null;
    int h = a.length;
    int w = a[0].length;
    int[][] c = new int[h][w];
    for(int y = 0; y < h; y++){
        for(int x = 0; x < w; x++){
            if(useAdd)
                c[y][x] = a[y][x] + b[y][x];
            else
                c[y][x] = a[y][x] - b[y][x];
        }
    }
    return c;
}

我非常想创建一些包含整个循环结构的通用方法来避免(几乎)重复代码。然而,如果“我所听到的”有一些合理的背景,据我所知最好避免这种情况。

最佳答案

如您所说,如果这是 C++,您将传递一个函数指针。好吧,如果您使用的是 Java 8,则有类似的东西 - BiFunction<Integer, Integer, Integer>

您的单一方法将如下所示:

private int[][] addOrSubtract(int[][] a, int[][] b, boolean useAdd){
    BiFunction<Integer, Integer, Integer> func = useAdd ? 
        ((a, b) -> a + b) : ((a, b) -> a - b);
    if(a == null || b == null || a.length != b.length || a.length < 1 || a[0].length != b.length)
        return null;
    int h = a.length;
    int w = a[0].length;
    int[][] c = new int[h][w];
    for(int y = 0; y < h; y++){
        for(int x = 0; x < w; x++){
            c[y][x] = func.apply(a[y][x], b[y][x]);
        }
    }
    return c;
}

如果您不使用 Java 8,那么我想您可以使用两种解决方案中的任何一种。我不认为他们有什么问题。请记住,过早优化是万恶之源!

关于java - 循环内的逻辑?或者更确切地说是两个独立的几乎相同的循环?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40758204/

相关文章:

java - 如果它们在组合中,如何从另一个类中正确调用java中的方法?

java - 如何确定 Java 中检索到的值类型?

javascript - 如何将数组中的 'double' 数字保存到新数组中

python - 即使条件为 true,带有 else 条件的 For 循环也会运行

java - 计算所有奇数数组索引的总和

java - 无法在单独的类中添加到根?

java - 哈希表比较器问题

c - C 中的 Switch case 帮助

c++ - 对我的 do-while 循环程序感到困惑

javascript - 在函数中使用数组作为参数