Java:如何用更易于维护的设计替换多个嵌套的if-else语句

Java:如何用更易于维护的设计替换多个嵌套的if-else语句,java,if-statement,design-patterns,java-8,functional-interface,Java,If Statement,Design Patterns,Java 8,Functional Interface,根据某些变量的值和/或类型以及某些函数的返回值,我需要执行不同的操作。原则上,所有的组合都是可能的 快速解决方案是测试嵌套的if-else语句中的所有组合,但生成的代码非常难看,很难维护和扩展(例如,我有新的条件要测试)。我在下面提供了一些示例代码。我正在使用Java SE 8: public static boolean myFunct () { return true; // hardcoded, it could also return false } public stati

根据某些变量的值和/或类型以及某些函数的返回值,我需要执行不同的操作。原则上,所有的组合都是可能的

快速解决方案是测试嵌套的
if-else
语句中的所有组合,但生成的代码非常难看,很难维护和扩展(例如,我有新的条件要测试)。我在下面提供了一些示例代码。我正在使用Java SE 8:

public static boolean myFunct () {
    return true;  // hardcoded, it could also return false
}

public static void main(String[] args) {

    int x = 1;  // hardcoded, it could also be =2
    Object o = new String();  // hardcoded, it could also be an Integer

    // here I begin to test to decide which action to execute
    if (x == 1) {
        if (o instanceof String) {
            if ( myFunct() ) {
                // do this if x==1 AND o is a String AND myFunct() returns true
                doAction1();  
            }
            else {
                doAction2();
            }
        }
        else if (o instanceof Integer) {
            if ( myFunct() ) {
                doAction3();
            }
            else {
                doAction4();
            }
        }
    }
    else if (x == 2) {
        if (o instanceof String) {
            if ( myFunct() ) {
                doAction5();
            }
            else {
                doAction6();
            }
        }
        else if (o instanceof Integer) {
            if ( myFunct() ) {
                doAction7();
            }
            else {
                doAction8();
            }
        }
    }
}

private static void doAction8() {
    // do some work...
}

private static void doAction7() {
    // do some work...
}

private static void doAction6() {
    // do some work...
}

private static void doAction5() {
    // do some work...
}

private static void doAction4() {
    // do some work...
}

private static void doAction3() {
    // do some work...
}

private static void doAction2() {
    // do some work...
}

private static void doAction1() {
    // do some work...
}
我读过一篇关于RuleEngine设计模式的文章,该模式可以优雅地应用于此类案例,并替换嵌套的
if-else
语句,但实际上找不到如何为我的案例实现它


提前感谢您的建议。

当您有多个条件,并且需要对这些条件的每个组合执行单独的操作时,一种方法如下所示

  • 首先,根据条件评估计算一个键(索引)
比如说,

|---------------|---------------|---------------|---------------|
|   condition1  |   condition2  |   condition3  |      key      |
|---------------|---------------|---------------|---------------|
|     true      |     true      |     true      |      111      |
|...............|...............|...............|...............|
|     true      |     true      |     false     |      110      |
|...............|...............|...............|...............|
|     true      |     false     |     false     |      100      |
|...............|...............|...............|...............|
|     true      |     false     |     true      |      101      |
|...............|...............|...............|...............|
|     false     |     true      |     true      |      011      |
|...............|...............|...............|...............|
|     false     |     true      |     false     |      010      |
|...............|...............|...............|...............|
|     false     |     false     |     false     |      000      |
|...............|...............|...............|...............|
|     false     |     false     |     true      |      001      |
|---------------|---------------|---------------|---------------|
如果您的案例使用了字符串键

String methodIndex = "";
methodIndex += (x == 1) ? "1" : "0";
methodIndex += (o instanceof String) ? "1" : "0";
methodIndex += (myFunct()) ? "1" : "0";
如果只有真-假条件存在,可能可以使用位操作更有效地执行此操作。否则,如果您具有多值条件(例如,
x
可以是
1
2
3
…),则计算字符串键会更容易

  • 然后根据计算出的键调用正确的操作(可能使用
    switch
    语句)

在将来的某个地方,这可能会引起您的兴趣。如果以后不使用
o
,为什么要使用
o instanceof X
?代码的目的是什么?我们知道您想做什么,但是……为什么?@AndrewTobilko我想让我的代码尽可能简洁,以关注我的实际问题。我的观点是类tyo的pe是决定执行哪个操作的条件之一。事实上,o实际上会在其他地方使用。@ditranet为了一个示例而使代码通用与从您尝试执行的操作中删除所有上下文是有区别的。如果我告诉您“做这件事,然后再做另一件事”然后我把我的请求变成了一般性的,但我也把我的请求弄得毫无意义。
switch (methodIndex) {
    case "111":
        doAction1();
        break;
    case "110":
        doAction2();
        break;
    case "101":
        doAction3();
        break;
    case "100":
        doAction4();
        break;
    case "011":
        doAction5();
        break;
    case "010":
        doAction6();
        break;
    case "001":
        doAction7();
        break;
    case "000":
        doAction8();
        break;
    default:
        System.out.println("No action defined");
}