有效地检查多个条件

Fro*_*men 8 java performance conditional

我有一种情况需要检查多种情况,其中每种组合都有不同的结果.在我的特定条件下,我有2个变量,它们是枚举类型,每个变量可以是2个不同的值.

enum Enum1
{
    COND_1,
    COND_2
}
enum EnumA
{
    COND_A,
    COND_B
}
Enum1 var1;
EnumA varA;
Run Code Online (Sandbox Code Playgroud)

这给了我4种可能的条件,这需要4种不同的结果.我想出了几种不同的方法,使用if语句或switch语句:

if(var1 == Enum1.COND_1 && varA == EnumA.COND_A)
{
    // Code
}
else if(var1 == Enum1.COND_1 && varA == EnumA.COND_B)
{
    // Code
}
else if(var1 == Enum1.COND_2 && varA == EnumA.COND_A)
{
    // Code
}
else if(var1 == Enum1.COND_2 && varA == EnumA.COND_B)
{
    // Code
}
Run Code Online (Sandbox Code Playgroud)

要么:

switch(var1)
{
    case COND_1:
        switch(varA)
        {
            case COND_A:
                // Code
                break;
            case COND_B:
                // Code
                break;
        }
        break;
    case COND_2:
        switch(varA)
        {
            case COND_A:
                // Code
                break;
            case COND_B:
                // Code
                break;
        }
        break;
}
Run Code Online (Sandbox Code Playgroud)

我已经想到了其他人,但不想用代码填写:P我想知道最好的方法是什么.我认为开关更容易阅读,但ifs更短.我认为如果开关有多种条件会很酷,但我还没有听说过.这也引出了一个问题:使用任意数量的变量和可能的值,最好的方法是什么?

Per*_*uss 9

对于你的小用例,我可能会去嵌套if语句.但是如果你有很多enum常量,那么使用流的模式可能会使你的代码更容易阅读和维护(性能损失很小).您可以使用如下流来解决它:

Stream.of(new Conditional(COND_1, COND_A, () -> {/* do something */}),
          new Conditional(COND_1, COND_B, () -> {/* do something */}),
          new Conditional(COND_2, COND_A, () -> {/* do something */}),
          new Conditional(COND_2, COND_B, () -> {/* do something */}))
      .filter(x -> x.test(var1, varA))
      .findAny()
      .ifPresent(Conditional::run);
Run Code Online (Sandbox Code Playgroud)

那将需要一个支持类:

class Conditional implements BiPredicate<Enum1, EnumA>, Runnable
{
    private final Enum1 var1;
    private final EnumA varA;
    private final Runnable runnable;

    public Conditional(Enum1 var1, EnumA varA, Runnable runnable) {
        this.var1 = var1;
        this.varA = varA;
        this.runnable = runnable;
    }

    @Override
    public boolean test(Enum1 enum1, EnumA enumA) {
        return var1 == enum1 && varA == enumA;
    }

    @Override
    public void run() {
        runnable.run();
    }
}
Run Code Online (Sandbox Code Playgroud)


jpa*_*jpa 7

这里的性能差异可能微不足道,所以我会关注简洁性和可读性.所以我只想if通过使用临时变量简化'sa bit':

boolean is_1 = (var1 == Enum1.COND_1);
boolean is_A = (varA == EnumA.COND_A);

if(is_1 && is_A)
{
    // Code
}
else if(is_1 && !is_A)
{
    // Code
}
else if(!is_1 && is_A)
{
    // Code
}
else if(!is_1 && !is_A)
{
    // Code
}
Run Code Online (Sandbox Code Playgroud)


Rol*_*lig 3

我更喜欢if没有嵌套的变体,因为它很短,并且您可以在一行中包含所有条件。

在调试过程中停止代码时,它可能会变得乏味,因为您必须跳过所有前面的条件,即 O(n)。执行代码时,这应该不重要,因为编译器可能会优化代码。

没有明显的最佳方法,因此您必须进行一些尝试。