老问题了,生成几个对象?

Rogice 2010-06-10 04:14:35

String s = "a" + "b" + "c" + "d" + "e";

此句代码从头至尾共创建了几个对象,
在其他论坛看到的这个帖子,众说纷纭啊,我等菜鸟被彻底搞迷糊了,还是来CSDN鉴定清楚
下面是那个帖子里的2个说发:
1。就创建了一个
String s = "a" + "b" + "c" + "d" + "e";
赋值符号右边的"a"、"b"、"c"、"d"、"e"都是常量
对于常量,编译时就直接存储它们的字面值而不是它们的引用
在编译时就直接讲它们连接的结果提取出来变成了"abcde"
该语句在class文件中就相当于String s = "abcde"
然后当JVM执行到这一句的时候, 就在String pool里找
如果没有这个字符串,就会产生一个

2.9个对象
分析如下:
String s只是一个对右边对象的引用不是对象,它引用的是右边表达式最后形成的对象,即"abcd"

再看右边 首先明确一点
String str=”aaa“;
上边的语句产生了一个对象
即右边是以双引号形式产生了一个String对象 此种形式的对象被存储在字符串池当中
题中右边的试子是以一下顺序来创建对象的
"a" 查找字符串池里没有与此字符串equal的字符串对象(注意是equal不是==)于是创建对象"a"
接着 "b" 同上 也在字符串池里创建对象"b"

接着 "a"+"b" 即 "ab" 同样 在字符串池里找不到equal的对象于是创建字符串池中对象"ab"

以此类推 产生9个对象 都存储在字符串池当中 分别是
"a"
"b"
"ab"
"c"
"abc"
"d"
"abcd"
"e"
"abcde"


个人比较倾向于第二个回答
...全文
648 64 打赏 收藏 举报
写回复
用AI写文章
64 条回复
切换为时间正序
请发表友善的回复…
发表回复
bfxyly 2010-08-04
  • 打赏
  • 举报
回复
当然是一个,实际上在编译后,池里只有"abcde",编译时编译器就将a,b,c,d,e连成一个字符串了
com_wangnl 2010-06-18
  • 打赏
  • 举报
回复
正确答案:1个
接分!!!
aibbhui 2010-06-18
  • 打赏
  • 举报
回复
生成了两个对象, 一个是在String池 , s是一个地址, 一个是在内存里面,堆栈的形式s分别指向a,b,c,d,e
goslingss 2010-06-18
  • 打赏
  • 举报
回复
可以参考这个帖子,讲的很清楚
http://topic.csdn.net/u/20080929/02/4e0ef626-98ee-4d6d-96ed-fe40afe8290b.html
goslingss 2010-06-18
  • 打赏
  • 举报
回复
[Quote=引用 55 楼 woshimajunwei 的回复:]
不要看很多人都说是一个你就觉得是一个!
原因:1. String类型一旦确定将不可更改。
2. String s = 这行代码执行过程:首先去Pool中找是否存在a,若不存在则创建,然后找是否存在b,若不存在则创建,最后调用cancat方法去连接字符串,并去查找是否存在ab,若不存在则创建。
3. 把ab的引用赋给s 。
上面有人说的反编译其实看到的并不是你“想当然……
[/Quote]

其实"a"+"b"它的值在编译时就确定了,而且是可以确定的。所以,会在string pool里新建一个对象“ab”,没有“a”和“b”。
wuyanfengstefanie 2010-06-18
  • 打赏
  • 举报
回复
路过,顶一下啊
QQ871103197 2010-06-18
  • 打赏
  • 举报
回复
[Quote=引用 59 楼 woshimajunwei 的回复:]
引用 58 楼 qq871103197 的回复:
引用 57 楼 woshimajunwei 的回复:
可能是我的措辞有问题,但你能从实质上推翻我的话,我服你!

java语言规定,对这种常量字符串(字面常量)要进行合并。注意是规定,那些说跟编译器有关的就别理会了。
比如String a = "a"+"b"+"c";编译器直接合并为a = "abc";
编译完得到class文件,里面执……
[/Quote]
注意提到StringBuffer的背景。
比如这样的例子
String a = "a";
String b = "b";
String c = a + b;
这时候a+b是两个变量连接,编译器无法进行直接的合并,它会考虑使用 StringBuilder连进行连接工作:
编译器处理为:
StringBuilder builder = new StringBuilder();
builder.append(a);
builder.append(b);
然后String c=builder.toString();
java5之前用StringBuffer替换。

String类的+操作会产生新对象,造成性能问题。多个String连接就看到优化的好处了,如
String a = "a";
String b = "b"
String c = "c";
String d = "d";
String e = "e";
String f = a + b + c + d + e;
最后一句将导致创建很多的String对象,"ab","abc","abcd","abcde"等。
而使用StringBuilder只需要创建一次,不断append。最后再转到String。

woshimajunwei 2010-06-18
  • 打赏
  • 举报
回复
[Quote=引用 58 楼 qq871103197 的回复:]
引用 57 楼 woshimajunwei 的回复:
可能是我的措辞有问题,但你能从实质上推翻我的话,我服你!

java语言规定,对这种常量字符串(字面常量)要进行合并。注意是规定,那些说跟编译器有关的就别理会了。
比如String a = "a"+"b"+"c";编译器直接合并为a = "abc";
编译完得到class文件,里面执行的语句功能就是a = "abc"了。
java虚……
[/Quote]
这个规定我是不大清楚,若真是这样,小弟没什么说的,但是如何解释StringBuffer比它效率高呢?
QQ871103197 2010-06-18
  • 打赏
  • 举报
回复
[Quote=引用 57 楼 woshimajunwei 的回复:]
可能是我的措辞有问题,但你能从实质上推翻我的话,我服你!
[/Quote]
java语言规定,对这种常量字符串(字面常量)要进行合并。注意是规定,那些说跟编译器有关的就别理会了。
比如String a = "a"+"b"+"c";编译器直接合并为a = "abc";
编译完得到class文件,里面执行的语句功能就是a = "abc"了。
java虚拟机只知道执行这么一句话,根本不知道"abc"到底是怎么来的。

对于分不清编译和运行两个过程的,扯什么都白搭。
woshimajunwei 2010-06-18
  • 打赏
  • 举报
回复
可能是我的措辞有问题,但你能从实质上推翻我的话,我服你!
QQ871103197 2010-06-18
  • 打赏
  • 举报
回复
[Quote=引用 55 楼 woshimajunwei 的回复:]
不要看很多人都说是一个你就觉得是一个!
原因:1. String类型一旦确定将不可更改。
2. String s = "a"+"b";这行代码执行过程:首先去Pool中找是否存在a,若不存在则创建,然后找是否存在b,若不存在则创建,最后调用cancat方法去连接字符串,并去查找是否存在ab,若不存在则创建。
3. 把ab的引用赋给s 。
上面有人说的反编译其实看到的并不是你“想当然……
[/Quote]
编译都处理成一个了,还从运行上讲“代码执行过程”有几个几个有意思吗?
先把编译和运行分清楚吧。
woshimajunwei 2010-06-18
  • 打赏
  • 举报
回复
不要看很多人都说是一个你就觉得是一个!
原因:1. String类型一旦确定将不可更改。
2. String s = "a"+"b";这行代码执行过程:首先去Pool中找是否存在a,若不存在则创建,然后找是否存在b,若不存在则创建,最后调用cancat方法去连接字符串,并去查找是否存在ab,若不存在则创建。
3. 把ab的引用赋给s 。
上面有人说的反编译其实看到的并不是你“想当然”的结果,而是编译器处理后的最终结果,当然只有一个了。
而且,之所以StringBuffer的append方法比用“+”连接效率高就在于它是可变的,自始至终都是一个对象,而用“+”需要创建多个对象!
期待有人提出异议!!!!!!!!
QQ871103197 2010-06-18
  • 打赏
  • 举报
回复
[Quote=引用 52 楼 ccqqct 的回复:]
引用 12 楼 natalya13 的回复:
动手写一下,然后反编译生成的class文件,就会发现代码变了,只有一个对象

那是因为编译时自动进行了优化,如果没有优化呢,产生几个呢.........
[/Quote]
这种优化是《java语言规范》规定的。所以,如果编译器不进行合并,不满足规范要求,就不是java编译器了。
angel6709 2010-06-18
  • 打赏
  • 举报
回复
木 料
ccqqct 2010-06-18
  • 打赏
  • 举报
回复
[Quote=引用 12 楼 natalya13 的回复:]
动手写一下,然后反编译生成的class文件,就会发现代码变了,只有一个对象
[/Quote]
那是因为编译时自动进行了优化,如果没有优化呢,产生几个呢.........
Ade子夜 2010-06-17
  • 打赏
  • 举报
回复
学习了!!
一个
QQ871103197 2010-06-17
  • 打赏
  • 举报
回复
对于连编译和运行都分不清的人说啥都白搭。
weiyuzhong 2010-06-17
  • 打赏
  • 举报
回复
不错,学习了
my5sky 2010-06-17
  • 打赏
  • 举报
回复
自己做个试验判断一下啊
my5sky 2010-06-17
  • 打赏
  • 举报
回复
String s = "a" + "b" + "c" + "d";
String str = "abcd";
if(str == s)
System.out.println(str);
}
加载更多回复(43)

62,620

社区成员

发帖
与我相关
我的任务
社区描述
Java 2 Standard Edition
社区管理员
  • Java SE
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧