簡體   English   中英

Java 的 switch 在底層是如何工作的?

[英]How does Java's switch work under the hood?

Java 的 switch 語句在底層是如何工作的? 它如何將正在使用的變量的值與案例部分中給出的值進行比較? 它使用==.equals() ,還是完全其他的東西?

我主要對 1.7 之前的版本感興趣。

兩者都不。 它使用lookupswitch JVM 指令,它本質上是一個表查找。 看一下下面例子的字節碼:

public static void main(String... args) {
  switch (1) {
  case 1:
    break;
  case 2:
    break;
  }
}

public static void main(java.lang.String[]);
  Code:
   Stack=1, Locals=1, Args_size=1
   0:   iconst_1
   1:   lookupswitch{ //2
                1: 28;
                2: 31;
                default: 31 }
   28:  goto    31
   31:  return

正如您從這個答案中看到的,Java switch (至少在 1.7 之前)並不總是編譯為==.equals() 相反,它使用表查找。 雖然這是一個非常小的微優化,但在進行大量比較時,表查找幾乎總是更快。

請注意,這僅用於檢查密集鍵的switch語句。 例如,檢查枚舉值的所有可能性可能會產生這個主要實現(內部稱為tableswitch )。

如果檢查更多稀疏填充的鍵集,JVM 將使用替代系統,稱為lookupswitch 相反,它將簡單地比較各種鍵和值,基本上對每種可能性進行優化==比較。 為了說明這兩種方法,請考慮以下兩個 switch 語句:

switch (value1) {
case 0:
    a();
    break;
case 1:
    b();
    break;
case 2:
    c();
    break;
case 3:
    d();
    break;
}

switch (value2) {
case 0:
    a();
    break;
case 35:
    b();
    break;
case 103:
    c();
    break;
case 1001:
    d();
    break;
}

第一個示例很可能使用表查找,而另一個示例(基本上)使用==比較。

這里復制

在字節碼中有兩種形式的開關:tableswitch 和lookupswitch。 一個假設一組密集的密鑰,另一個稀疏。 請參閱 JVM 規范中對編譯開關的描述。 對於枚舉,找到序數,然后代碼繼續作為 int 情況。 我不完全確定將如何實現 JDK7 中的 String 小功能的建議切換。

但是,大量使用的代碼通常在任何合理的 JVM 中編譯。 優化器並不完全是愚蠢的。 別擔心,按照通常的啟發式方法進行優化。

你會在 這里找到詳細的答案

1.Java 7到來之前,它是"==" ,因為我們可以使用integer 和 char 進行 switch case,而且由於它們是原始的,所以它必須是"=="

2.Java 7在 switch case 中也允許String ,並且 String 作為object ,使用".equals"

我想補充一點…… "=="用於比較Object Reference Variable而不是對象本身 使用".equals"我們比較對象

開關適用於 byte、short、char 和 int 原始數據類型。 它還適用於枚舉類型(在 Enum Types 中討論)、String 類和一些包裝某些原始類型的特殊類:Character、Byte、Short 和 Integer。 (Java 1.6)

雖然基元與==進行比較,但switch方法肯定在 Java 1.6(及更早版本)中使用了這種比較。

如果使用 1.7 之前的 Java,我假設它使用

==

因為對於 int 你不能做 equals 例如在枚舉的情況下,equals 和 == 將返回相同的

編輯

我的假設是錯誤的,它使用了一個查找表,在字節碼中它會喜歡:

 tableswitch

如果您使用原始類型,例如整數,那么java 將使用==來比較它們如果您使用字符串,那么java 將使用equals()方法來測試字符串是否相等。 如果您使用帶枚舉的 switch 語句,則==equals()是相同的,因此使用哪一個並不重要。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM