爲什麼其打印X88輸出,從我所預期的不同
public static void main(String [] args)
{
char x = 'X';
int i = 0;
System.out.print(true ? x : 0);
System.out.print(false ? i : x);
}
爲什麼其打印X88輸出,從我所預期的不同
public static void main(String [] args)
{
char x = 'X';
int i = 0;
System.out.print(true ? x : 0);
System.out.print(false ? i : x);
}
在第一print
語句,條件表達式的類型是字符(即「X」),因爲section 15.25 of the JLS該部分(其是關於條件表達式的類型)適用於:
如果一個的操作數是類型T,其中T是字節,短或字符,另一個操作數是類型爲int的常量表達式,其值可用T類型表示,則條件表達式的類型爲T.
所以第一條語句打印「X」。
在第二個print
聲明中,該部分不適用,因爲i
不是的一個常量表達式。取而代之的是,本部分中適用:
否則,二進制數值提升(§5.6.2)被施加到操作數類型,以及條件表達式的類型是所述第二和第三操作數的提升的類型。請注意,二進制數字提升會執行拆箱轉換(§5.1.8)和值集轉換(§5.1.13)。
二進制數字升級將char'X'轉換爲int(88),第二個語句打印「88」 - 因此爲「X88」的總體結果。
對於第一條語句System.out.print(false ? x : 0);
編譯器認爲你要打印一個char所以0將被視爲一個char(編譯時)。
當你做System.out.print(false ? i : x);
編譯器認爲你要打印一個整數,所以它會嘗試轉換(擴大)「X」到一個整數,是88
一個有趣的事情是,如果你嘗試要做到這一點:
System.out.print(true ? x : i);
由於i
不能(這需要縮小)視爲一個字符將打印88
另一件事是這裏interessant:
System.out.print(true ? x : 65536);
這一次的值65536
不能被認爲是在編譯時一個char(用於一個字符的最大值是65535
[@see Character.MAX_VALUE]),所以它會被認爲是一個int,所以X也將是。
概括地說,如果操作數中的一個是int和其他炭,有兩種可能的轉換:
爲了避免無用的損失,Java會選擇第二個選項。
當您執行System.out.print(false ? x : 0);
時,0在編譯時轉換爲char(因爲編譯器知道不會失去精度)。
資源:
是System.out.print(真×:0); 爲什麼不在這個聲明中打印爲整數 – 2010-10-02 07:10:02
@ user457708:我用一個JLS報價編輯了我的答案來回答這個問題。 – 2010-10-02 07:13:06
@ user457708,我更新以向您展示更多解釋和技巧;) – 2010-10-02 07:21:29
由於表達false ? i : x
被看作是由編譯器返回一個整數。由於您使用的是char
,「X」在ASCII中爲88,因爲它們兼容,所以它被視爲整數。
就我個人而言,我認爲這裏至少應該有一個編譯器警告。
在第二個三元組中,如果參數必須是相同類型,否則其中一個隱式轉換。
在你的榜樣,x爲字符轉換成int,而「X」有88
其他人已經回答了爲什麼出現這種情況的ASCII碼。
如果要X
要打印,鑄表達式的值回char
爲:
System.out.print((char)(false ? i : x)); // prints X
,或者您也可以投i
到char
使得表達式的類型變得char
爲:
System.out.print(false ? (char)i : x); // prints X
它在JLS的§15.25中有解釋。
否則,如果第二個和第三個操作數 必須是 轉換(§5.1.8)到數字類型,然後 有幾種情況類型:
這適用於報表,因爲char和int都是數字類型,所以5.1.8適用。因此,我們看看下面(摘錄)規則:
[...]
- 如果一個操作數的類型是其中T是字節,短,或 炭,和另一個操作數的類型是int其 值是類型T可表示的 常量表達式,然後 條件表達式 的類型是T.
這適用於第一個,因爲0是int類型的常量表達式。 T是,char
,這就是爲什麼它打印爲X.
[...]
- 否則,二進制數值提升(§5.6.2)被施加到操作數 類型和 條件表達式的類型是促進 類型的第二和第三運算數的。 請注意,二進制數字提升 執行拆箱轉換(§5.1.8) 和值集轉換(§5.1.13)。
這適用於第二,因爲沒有別的。 :) §5.6.2的相關規則很簡單:
否則,兩個操作數都轉換爲int類型。
Unicode碼點 'X' 是88.
+1,很好的答案。 – 2010-10-02 07:21:22
+1,很好的答案。 – 2010-10-02 07:52:47
不,他們都不是Character。看到我的答案。 – 2010-10-02 07:14:08
@Matthew:哎呀,錯誤的一點,但正確的想法 - 編輯。 (現在修復,如果你想刪除downvote :) – 2010-10-02 07:16:15
當然。 :)我知道你會很快解決它。 – 2010-10-02 07:22:49