面试之字符串之谜 - String.intern() 字符串常量池

      一、String 变量创建分析

(1)  在HotSpot VM里实现的string pool功能的是一个StringTable类,它是一个Hash表,默认值大小长度是1009;这个StringTable在每个HotSpot VM的实例只有一份,被所有的类共享。字符串常量由一个一个字符组成,放在了StringTable上。
(2)   在JDK6.0中,StringTable的长度是固定的,长度就是1009,因此如果放入String Pool中的String非常多,就会造成hash冲突,导致链表过长,当调用String#intern()时会需要到链表上一个一个找,从而导致性能大幅度下降;
(3)  在JDK7.0中,StringTable的长度可以通过参数指定 -XX:StringTableSize=xxxxxx

      String lily = "Lily";

      String tomsy = "tom" + "sy";

       直接赋值,则为常量,在编译期间就已经确定,直接存储在字符串常量池中,对于 tomsy jvm做了优化不会创建tom 、sy 只会创建tomsy在常量池中,此时lily.intern() 就是一个常量

      String lyli_1 = new String("Lily");

      String tomsy = new String("tom") + new String("sy");

      创建对象,变量的值在程序运行期间确定。首先lily_1会在字符串常量池查找是否有没有创建Lily,然后在堆上创建一个String对象实例 lily_1指向该实例。同理tomsy 也会在字符串常量池查找或创建tom、sy两个常量,同时在堆上创建两个String对象以及合成后的tomsy三个对象。

       tomsy.intern();

       String tomsy_1 = "tomsy";

     此时在执行intern()方法,先查找字符串常量池中是否已存在,如果不存在则会在常量池添加一份tomsy对象的引用,返回该引用,此时tomsy_1赋值的时候则会直接把该引用返回给tomsy_1

     System.out.println(tomsy == tomsy_1); 返回true

 

String mess = "abc";

String mess1 = new String("abc");

String a = mess.intern();

String b = new String("abc").intern();

mess == a   true

mess == mess1  false

a == b true

intern() 首先会检测 字符串常量池中是否有此字符串 有则直接返回 引用,否则新建返回改引用,

new String("abc")  在堆中创建对象 同时 会检测 字符串常量池中是否有改字符串 无则新建 有则什么也不做 返回的是 堆中的对象的引用

 

 

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值