美文网首页
2017/9/12 String.intern()

2017/9/12 String.intern()

作者: atai | 来源:发表于2017-09-12 15:39 被阅读0次

参考:

《深入理解java虚拟机》 p56-57  

揭开 String.intern() 那神秘的面纱

深入分析String.intern和String常量的实现原理

1.  new String("abc")创建了几个对象??

记住。这个与JDK版本无关。

如果常量池原来有个“abc”,那么只创建一个对象;

如果常量池中原来没有字符串"abc",那么就会创建两个对象。

2. String.intern()方法(Native方法) 1.6复制的是实例 1.7复制的是引用

jdk1.6时:如果字符串常量池中已经包含一个等于此String对象的字符串,则返回代表池中这个字符串的String对象;否则,将此String对象包含的字符串添加到常量池中,并且返回此String对象的引用。(常量池分配在永久代)

JDK1.7时:Java 7将常量池从PermGen区移到了Java堆区,执行intern操作时,如果常量池已经存在该字符串,则直接返回字符串引用,否则 复制该字符串对象的引用 到常量池中并返回 (首次出现原则)

具体区别分析见《深入分析String.intern和String常量的实现原理

3.图解说明

验证String.intern()方法在jdk1.6和1.7中的差异

上述代码在JDK1.6时输出false ,false  JDK 1.7时输出true,false

JDK 1.6

从这幅图可以看出,在调用s1.intern()时,常量池中不存在StringTest,因此复制了一份StringTest的实例置于常量池中,并返回常量池中StringTest的引用,而s1指向的是Java堆中的StringTest,二者并不相同,返回false;

java字符串本身就在常量池中存在(可能是jvm虚拟机放进去的)。这时候调用s2.intern(),返回的是常量池中java 的引用,s2指向的是Java堆中的java,二者并不相同,返回false。

JDK 1.7

JDK1.7时,常量池被移到了java堆区。在常量池中没有找到StringTest,只是在常量池中记录下首次出现的实例地址,因此s1.intern()和s1指向的是同一个StringTest,所以结果为true;

而在常量池中找到了java,返回的是常量池中java的地址,与s2不想同。

因此JDK1.7中输出如下:

JDK 1.7输出结果

需要注意的是,s3.intern()==s3也返回false。

以下是自己的推测;

(1)根据第1条,new String(“abc”)应该是等价于new StringBuilder(“abc”).toString()。 s3会在字符串常量池中创建“StringTest”对象,也会在对中创建对象。因此s3.intern()中StringTest不符合首次出现,不会复制指向堆中StringTest的引用到常量池中,因此s3.intern()与s3不相等。

(2) 而s1中,应该是常量池存在String,Test。但是不存在StringTest,仍然符合首次出现原则,因此会复制堆中StringTest的引用到常量池中。

上述(2),用“计算机软件进行验证”。

常量池不存在“计算机”与“软件” s1的建立在常量池中存放了“计算机”和“软件”

从上述结果验证了自己推测的(2)。s1在常量池中建立了“计算机”和“软件”对象。  这样s4.intern()和s5.intern()都不符合首次出现原则,因此返回false。

相关文章

  • 2017/9/12 String.intern()

    参考: 《深入理解java虚拟机》 p56-57 揭开 String.intern() 那神秘的面纱 深入分析St...

  • String

    深入分析String.intern和String常量的实现原理 占小狼 关注 2016-12-08 18:26 ·...

  • 果果第一次新加坡之行开始啦!

    2017年12月9日

  • String.intern()

    String.intern()原理String.intern()是一个Native方法,底层调用c++的Strin...

  • 2018-09-21

    2017年9月12日-2018年9月20日,再见!

  • 美音学习1

    2017年9月9日~12日,美音发音小结整理。

  • 浅谈Java String.intern()

    简书 占小狼转载请注明原创出处,谢谢! String.intern()原理 String.intern()是一个N...

  • String.intern()方法作用

    String.intern()方法设计的初衷:重用字符串,节省内存 JDK1.6中使用String.intern(...

  • 医学生APP维护文档

    2017/9/12 1.修复首页轮播区偶发白屏现象 2017/9/6-2017/9/7 1.升级现有库到最新稳定版...

  • 2017-12-31

    2017-12-301 禾隆李亮 2017-12-3119:23 · 字数 370 · 阅读 9 · 日记本 20...

网友评论

      本文标题:2017/9/12 String.intern()

      本文链接:https://www.haomeiwen.com/subject/lpucsxtx.html