2010年10月3日日曜日

JDK7のString in switch(2)

文字列リテラルのhashCodeがぶつかったときどうなるか調べた。
予想通り、最初のhashCodeでのジャンプの後でequalsでそれぞれ確認して実際の処理に分岐するための値を設定していた。


java.lang.Stringを書き換えてbootclasspath(-J-Xbootclasspath/-bootclasspathの両方)で指定してもうまくいかなかったので、検索して見つけたテストコードを参考にやってみた。hashCodeが0になるパターンをいくつか指定している。


public class Test {
    public static void main(String[] args) {
        String s  = "\u0000";
        switch (s) {
        case "":
            System.out.println("empty");
            break;
        case "\u0000":
            System.out.println("\\u0000");
            break;
        }
    }
}

28-34で""か判定して、""じゃなければ42-48で"\u0000"か判定してる。
8: invokevirtual #3                  // Method java/lang/String.hashCode:()I
        11: lookupswitch  { // 1
                       0: 28
                 default: 53
            }
        28: aload_2
        29: ldc           #2                  // String
        31: invokevirtual #4                  // Method java/lang/String.equals:(Ljava/lang/Object;)Z
        34: ifeq          42
        37: iconst_1
        38: istore_3
        39: goto          53
        42: aload_2
        43: ldc           #5                  // String
        45: invokevirtual #4                  // Method java/lang/String.equals:(Ljava/lang/Object;)Z
        48: ifeq          53
        51: iconst_0
        52: istore_3
        53: iload_3
        54: lookupswitch  { // 2
                       0: 80
                       1: 91
                 default: 99
            }
        80: getstatic     #6                  // Field java/lang/System.out:Ljava/io/PrintStream;
        83: ldc           #7                  // String empty
        85: invokevirtual #8                  // Method java/io/PrintStream.println:(Ljava/lang/String;)V
        88: goto          99
        91: getstatic     #6                  // Field java/lang/System.out:Ljava/io/PrintStream;
        94: ldc           #9                  // String \u0000
        96: invokevirtual #8                  // Method java/io/PrintStream.println:(Ljava/lang/String;)V
        99: return

0 件のコメント:

コメントを投稿