黑马程序员技术交流社区
标题:
String a="abc";
[打印本页]
作者:
观决
时间:
2014-6-4 15:14
标题:
String a="abc";
本帖最后由 观决 于 2014-6-4 18:16 编辑
最近看到下面这样一段话 我晓得String a="abc" 是现在常量池中看有没有 有就直接把对象引用复制给a 没有创建一个在复制给a
我不晓得他下面那个红色字体的
先在heap中创建 然后移到常量池中(不是直接在常量池中创建)
这是正确的吗(或者有哪本书中有这样写)? 有哪位晓得这个的过程的 麻烦说一下
当执行String a=“abc”;时,JAVA虚拟机会在栈中创建三个char型的值‘a’、‘b’和‘c’,
然后在堆中创建一个String对象
,它的值(value)是刚才在栈中创建的三个char型值组成的数组{‘a’,‘b’,‘c’},
最后这个新创建的String对象会被添加到字符串池中。
作者:
观决
时间:
2014-6-4 18:16
本帖最后由 观决 于 2014-6-4 18:20 编辑
常量池在java用于保存在编译期已确定的,已编译的class文件中的一份数据
String对象,一个是通过""双引号创建的,一个是通过new创建的.只不过他们创建的时期不同,一个是编译期,一个是运行期! 我觉得这样才对 这样上面那句
先在heap中创建 然后添加到字符串池中就不对了
应该就是在编译时 发现""这样创建的 就看字符串常量池中有没有 有就将对象引用复制给a 不会再heap里面new创建的才是heap里
作者:
观决
时间:
2014-6-4 21:18
本帖最后由 观决 于 2014-6-4 21:20 编辑
好吧 虽然问题被我结束了 我还是吧自己现在的理解说下 刚才看到很多 貌似懂了一些
String a="haha" 属于字符串的常量池 这个是在编译期就存在的 被写入了class文件中
然后class被加载到 jvm 中时 jvm在Method Area区域给他开辟一个空间 用于常量池
然后 jvm底层是这样的 Method Area 属于堆 只不过GC一般不处理它 所以在jvm运行起来时 不会有上面的那一步先在堆中创建 再添加到常量池 (直接作用常量池 回去找常量池入口)
下面是JVM 详细过程
// 这个过程是在网上看到
http://developer.51cto.com/art/200805/73338.htm 这是链接 这里不晓得怎么插入链接插入了没反应 要看的自己去复制吧我搞大点
对于String a = "haha" ,它的虚拟机指令:
0: ldc #16; //String haha
2: astore_1
3: return
对于上面虚拟机指令,其各自的指令流程在《深入JAVA虚拟机》这样描述到(结合上面实例):
ldc指令格式:ldc,index
ldc指令过程:
要执行ldc指令,JVM首先查找index所指定的常量池入口,在index指向的常量池入口,JVM将会查找CONSTANT_
Integer
_info,CONSTANT_
Float
_info和CONSTANT_
String
_info入口。如果还没有这些入口,JVM会解析它们。
而对于上面的hahaJVM会找到CONSTANT_String_info入口
,同时,将把指向被拘留String对象(由解析该入口的进程产生)的引用压入操作数栈。
astore_1指令格式:astore_1
astore_1指令过程:
要执行astore_1指令,JVM从操作数栈顶部弹出一个引用类型或者returnAddress类型值,然后将该值存入由索引1指定的局部变量中,即将引用类型或者returnAddress类型值存入局部变量1。
return 指令的过程:
从方法中返回,返回值为void。
欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/)
黑马程序员IT技术论坛 X3.2