switch文をコンパイルしたときに何のバイトコードが出力されるかは、case句に指定した値の離散具合で変化するようです。
tableswitchとlookupswitchが使い分けられるようなのですが、その使い分けの条件が分かりません。
http://blog.livedoor.jp/lisper/archives/16161645.html
こちらのサイトで式が載っていたのですが、これで合ってますか? 式中の「^」って排他的論理和?
色々な条件でswitch文を書いて、javapで逆アセンブルして検証してみようかとも思ったのですが…
すいませんが教えてください。
推測です。
どのようなバイトコードになるかは、Java コンパイラ依存ではないかと思います。極端な話、自分でコンパイラを書けば、常に tableswitch を使う版とかも作れます。ご質問は、メジャーなコンパイラでどうなるかということかと思いますけれども。
ソースが公開されているコンパイラでしたら、ソースコードを読むほうが早いかもしれません。Sun Microsystems の JDK も公開されていましたよね(うろ覚え)。
なお、リンク先ページの式中の「∧」は論理記号の「かつ」(MS-IME で「かつ」で変換できました)だと思います。「n * 4 - 10 >= e ∧ n > 3」は、「n * 4 - 10 >= e && n > 3」と考えればいいと思います。
直接の回答にはなっていませんが、ご参考になれば。
あー、なるほど!「∧」は「かつ」っていう意味ですね!腑に落ちてスッキリしました。
http://openjdk.java.net/
ここからJDK7のソースを落としてきて読んでみたんですが、難しくて、switch文のコード生成を行っている部分にたどり着くことができませんでした…
Eclipseに付属しているJavaコンパイラのECJですが、それのソースを読んでみた所、こちらは分かりやすかったです。
http://kickjava.com/src/org/eclipse/jdt/internal/compiler/ast/Sw...
上のページが、switchのコード生成しているらしき部分のソースコードです。
これを読むと、
・case句の値の最大と最小の差が、case句の数の2.5倍より小さければtableswitch、そうでなければlookuptable
という処理になっていました。JDK5の条件(リンク先ページの式)と違っていますね。
おっしゃるとおり、コンパイラ依存のようですね。
とても参考になりました。ありがとうございました。