Does an effective switch require self-criticism?

Apparently, when expressions are compiled differently depending on how constants are denoted:

 object SwitchOverConstants { val foo = 1 val bar = 2 val baz = 3 fun one(x: Int) = when (x) { foo -> "foo" bar -> "bar" baz -> "baz" else -> "else" } fun two(x: Int) = when (x) { SwitchOverConstants.foo -> "foo" SwitchOverConstants.bar -> "bar" SwitchOverConstants.baz -> "baz" else -> "else" } } 

Here is the byte code for one :

  0: iload_1 1: istore_2 2: iload_2 3: getstatic #15 // Field foo:I 6: if_icmpne 14 9: ldc #34 // String foo 11: goto 40 14: iload_2 15: getstatic #22 // Field bar:I 18: if_icmpne 26 21: ldc #35 // String bar 23: goto 40 26: iload_2 27: getstatic #27 // Field baz:I 30: if_icmpne 38 33: ldc #36 // String baz 35: goto 40 38: ldc #38 // String else 40: areturn 

And here is the byte code for two :

  0: iload_1 1: tableswitch { // 1 to 3 1: 28 2: 33 3: 38 default: 43 } 28: ldc #34 // String foo 30: goto 45 33: ldc #35 // String bar 35: goto 45 38: ldc #36 // String baz 40: goto 45 43: ldc #38 // String else 45: areturn 

Why do I need to define constants with the class name in order to get an efficient table lookup?

+6
source share
1 answer

You must mark each constant with the const modifier, then optimization will be performed.

By the way, in the latest version of Kotlin, the bytecode for both functions is identical.

0
source

Source: https://habr.com/ru/post/985805/


All Articles