一尘不染

效率:将语句切换到if语句

java

PMD 告诉我

少于3个分支的交换机效率低下,请改用if语句。

这是为什么?为什么是3?他们如何定义效率?


阅读 208

收藏
2020-12-03

共1个答案

一尘不染

因为switch语句是使用两个特殊的JVM指令lookupswitch和编译的tableswitch。在处理很多案例时它们很有用,但是当您只有很少的分支机构时,它们会导致开销。

if/else相反,一条语句被编译为典型的je jne…链,这些链速度更快,但在长分支链中使用时需要更多的比较。

您可以通过查看字节码来看到差异,无论如何我都不担心这些问题,如果有什么可能成为问题,那么JIT会解决它。

实际示例:

switch (i)
{
  case 1: return "Foo";
  case 2: return "Baz";
  case 3: return "Bar";
  default: return null;
}

编译成:

L0
 LINENUMBER 21 L0
 ILOAD 1
 TABLESWITCH
   1: L1
   2: L2
   3: L3
   default: L4
L1
 LINENUMBER 23 L1
FRAME SAME
 LDC "Foo"
 ARETURN
L2
 LINENUMBER 24 L2
FRAME SAME
 LDC "Baz"
 ARETURN
L3
 LINENUMBER 25 L3
FRAME SAME
 LDC "Bar"
 ARETURN
L4
 LINENUMBER 26 L4
FRAME SAME
 ACONST_NULL
 ARETURN

if (i == 1)
  return "Foo";
else if (i == 2)
  return "Baz";
else if (i == 3)
  return "Bar";
else
  return null;

被编译成

L0
 LINENUMBER 21 L0
 ILOAD 1
 ICONST_1
 IF_ICMPNE L1
L2
 LINENUMBER 22 L2
 LDC "Foo"
 ARETURN
L1
 LINENUMBER 23 L1
FRAME SAME
 ILOAD 1
 ICONST_2
 IF_ICMPNE L3
L4
 LINENUMBER 24 L4
 LDC "Baz"
 ARETURN
L3
 LINENUMBER 25 L3
FRAME SAME
 ILOAD 1
 ICONST_3
 IF_ICMPNE L5
L6
 LINENUMBER 26 L6
 LDC "Bar"
 ARETURN
L5
 LINENUMBER 28 L5
FRAME SAME
 ACONST_NULL
 ARETURN
2020-12-03