自己想的一道題,算是30%原創(chuàng)吧?
String a=new String("Hello");
? a+="World";
?問:a的內(nèi)容最后是什么?
???????? 這兩個(gè)語句,共生成了幾個(gè)Java對(duì)象?
簡單不?看樣子非常簡單吧,呵呵。
第一問:a(確切地說a引用的內(nèi)容)是HelloWorld
?
第二問: 兩個(gè)語句,一共生成了幾個(gè)對(duì)象?
????看第一個(gè)語句,說實(shí)話,用這種方式初始化String,實(shí)在是代碼垃圾。這先不管啦。這個(gè)語句是老生長談,一個(gè)或兩個(gè)對(duì)象。
??? 為何?第一次執(zhí)行時(shí)創(chuàng)建了二個(gè), 一個(gè)為字面量"Hello"(它本身是一個(gè)String對(duì)象), 一個(gè)為new String("Hello")(它是通過new創(chuàng)建的, 功能上和字面量"foo"完全一樣, 但卻是另一個(gè)對(duì)象).
第二次執(zhí)行時(shí), 只創(chuàng)建一個(gè), 即new String("Hello"), 這是因?yàn)? "Hello"作為String字面量, 是存在于String Pool里面的, 第二次使用它時(shí), 直接指向原有的String, 而不再創(chuàng)建新的String; 但new String("Hello")卻每執(zhí)行一次都創(chuàng)建一個(gè)新的,完全一樣的String對(duì)象.
???第二個(gè)語句呢?
???? 3個(gè)對(duì)象。
???? 首先是“World”,毋庸質(zhì)疑。
???? 那么然后呢?注意了,String是final類,不可改變。平時(shí)我們寫Java會(huì)有個(gè)錯(cuò)覺,stringA+stringB就以為是前者尾巴接上后者腦袋。的確,在C/C++里就是如此。一點(diǎn)兒錯(cuò)都沒有。
??? 但是Java不是,Java設(shè)計(jì)者為了更多方面的考慮,他們把String設(shè)計(jì)成了final。
??? 看一下JVM匯編指令吧
? 0:?aload_0
?? 1:?invokespecial?#1; //Method java/lang/Object."<init>":()V
?? 4:?return
static void inti();
? Code:
?? 0:?new?#2; //class java/lang/String
?? 3:?dup
?? 4:?ldc?#3; //String Hello
?? 6:?invokespecial?#4; //Method java/lang/String."<init>":(Ljava/lang/String;)V
?? 9:?astore_0
?? 10:?new?#5; //class java/lang/StringBuilder
?? 13:?dup
?? 14:?invokespecial?#6; //Method java/lang/StringBuilder."<init>":()V
?? 17:?aload_0
?? 18:?invokevirtual?#7; //Method java/lang/StringBuilder.append:(Ljava/lang/String;)Ljava/lang/StringBuilder;
?? 21:?ldc?#3; //String Hello
?? 23:?invokevirtual?#7; //Method java/lang/StringBuilder.append:(Ljava/lang/String;)Ljava/lang/StringBuilder;
?? 26:?invokevirtual?#8; //Method java/lang/StringBuilder.toString:()Ljava/lang/String;
?? 29:?astore_0
?? 30:?return
}
仔細(xì)看一下我做的標(biāo)記,JVM給我們生成了一個(gè)StringBuilder類。(我用的是JDK5,舊版本是StringBuffer類,單單這一點(diǎn)小改動(dòng)就能讓Java的速度提高很多)。讓后用append方法載入Hello和World兩個(gè)String的引用(明確地說轉(zhuǎn)化成字符數(shù)組)。
當(dāng)載入完成后,StringBuilder實(shí)例調(diào)用toString,生成一個(gè)新的String實(shí)例(暫時(shí)稱為TempString)。
?最后把引用a指向TempString
總結(jié):兩句語句總共生成了4個(gè)或5個(gè)Java類實(shí)例
PS:Java中沒有指針實(shí)在是太不方便了。特別是在操作原始數(shù)據(jù)類型的時(shí)候。個(gè)人認(rèn)為Java應(yīng)該在這點(diǎn)上學(xué)學(xué)C#。指針不是洪水猛獸,對(duì)優(yōu)秀程序員而言,指針是編程中的一種享受。
??????? 希望“海豚”(Java7)能出現(xiàn)指針吧---很不現(xiàn)實(shí),還是等開源后的Java版本吧