2011-03-28 35 views
7

Java不能對操作符進行重載,但+StringInteger以及其他一些類可以正常工作。這怎麼可能?+爲什麼在Java中使用Strings?

更新:
爲什麼這項工作?

Integer i = 4; 
Integer p = 5; 

System.out.println(i*p); // prints 20 

回答

7

+不是運算符重載的例子。 +作爲連接算子構建爲語言算術加法運算符。

這意味着,寫一個程序使用Java的人不能超載運營商,但據Java語言的語法而言,+被定義爲級聯和加法運算符。

編輯

它適用於其他類,如IntegerDouble因爲autoboxing

如果您查看執行字符串連接的Java程序的字節碼,您會看到它創建了StringBuilder並使用了append()方法。 Java編譯器會看到+運算符,並意識到操作數是字符串而不是原始類型(如int)。

如果您查看整數加法的程序的字節碼,您將看到它使用指令iadd執行整數加法。這是因爲編譯器意識到操作數爲+操作是整數。

就像Integer i = 4這樣做,字節碼會顯示你實際上在做Integer i = Integer.valueOf(4)。這被稱爲自動裝箱。後來,當你這樣做i + p,其中兩個ipInteger型的,生成的字節碼會告訴你正在做i.intValue() + p.intValue(),這裏的返回類型的兩種方法都int(實際字節碼指令再次,是iadd )。

這就是爲什麼+工作Integer即使它們不是實際的原始類型。

+0

謝謝!是否有支持自動裝箱的所有類的列表? – VextoR 2011-03-28 20:20:36

+1

我相信'int','float','double','boolean','short'和'byte'存在自動裝箱。 – 2011-03-28 20:23:18

6

它的工作原理像整數因爲autoboxing原始包裝。

它適用於字符串,因爲這是一個special case for concatenating strings

Java語言提供對字符串連接運算符(+)的特殊支持,以及對其他對象的字符串轉換。字符串連接通過StringBuilder(或StringBuffer)類及其append方法實現。字符串轉換通過toString方法實現,由Object定義並由Java中的所有類繼承。有關字符串連接和轉換的更多信息,請參閱Gosling,Joy和Steele,Java語言規範。

4

+是一種內置操作。這是一個例外,不是一個規則。

+0

謝謝。但是爲什麼它可以與Integer等其他類一起工作,請參閱更新後的問題 – VextoR 2011-03-28 20:01:16

+0

運算符在將源代碼消解到Java IL時由編譯器簡單分析。有IL級別的指令可以對數字進行加,減,乘等操作。 *另外*,+是硬編碼,可與字符串一起使用;編譯器會將「a」+「b」翻譯爲IL級別的指令以連接「a」和「b」。 – KeithS 2011-03-28 20:03:53

2

Java不允許定製操作符重載,但是編譯器仍然可以通過編譯器開發人員認爲的String1 + String2的== String1String2,並替換爲正確的拼接方法調用+操作被告知。

2

Java語言爲字符串連接運算符(+)提供了特殊支持,併爲其他對象轉換爲字符串提供了特殊支持。

String s = "string 1" + "string 2"; 

什麼是真正的執行是

(new StringBuilder()).append("string 1").append("string 2").toString() 
1

正如@yan說,這是例外,而不是規則。字符串在Java中有特殊的地位。 Java語言規範的整個小節以+的角色作爲字符串連接運算符:§15.18.1

關於您的更新,這是另一種特殊情況。 Java是有時,視情況而定,足夠智能,可以在需要String時,將不是String的事件轉換爲String。其中一種特殊情況是您所描述的情況,原始信息出現在需要String的地方。原語首先轉換爲其參考類型— Integer,Double,& c。 —,然後通過toString()方法轉換成String

另一種特殊情況是當一個String和一個非String正在與串並置運算符+結合,如在JLS §5.4 — String Conversion說明。

爲了完整:+在其更常見的「添加數字在一起」的作用在§15.18的其他部分中描述,§15.18.2 — Additive Operators (+ and -) for Numeric Types

相關問題