深入Java核心 Java 内存分配(2)_字符串的存储

***字符串常量池 

String是一个特殊的包装类数据。可以用:
  String str=new String("abc");
  String str="abc";
  两种的形式来创建。
  1.第一种是用new()来新建对象的,它会在存放于堆中。每调用一次就会
创建一个新的对象。
  2.而第二种是先在栈中创建一个对String类的对象引用变量str,然后通过符号
引用去字符串常量池里找有没有"abc",如果没有,则将"abc"存放进字符串常量池
然后通过符号引用去字符串常量池,如果已经有”abc” 则直接令str指向“abc”。 

***字符串常量的加载

  字符串常量在编译期间就确定了。
案例1:
  String s0="abc";
  String s1="abc";
  String s2="a"+"bc";
  System.out.println(s0==s1);//true
  System.out.println(s1==s2);//true
  
  1.Java 会确保#一个字符串常量只有一个拷贝#
  2.字符串常量,它们在编译期就被确定了。
(当一个字符串由多个字符串常量连接而成时,它自己肯定也是字符串常量) 常量+常量=常量
  3.用new String() 创建的字符串不是常量,不能在编译期就确定

案例2:
  String s0="abc";
  String s1=new String("abc");
  String s2="a"+new String("bc");
  System.out.println(s0==s1);//false
  System.out.println(s0==s2);//false
  System.out.println(s1==s2);//false
  
  1.s0 是常量池中"abc"中的引用
  2.s1 因为在编译期间无法确定,所以是运行时创建的对象。  
  3.s2 因为在后半部分无法在编译期间确定,所以也是一个
新的对象。  

***String  intern()方法

  1.存在于.class文件中的常量池,在运行期被JVM装载
  2.String的 intern()方法就是#扩充常量池#的 一个方法

  3.当一个String实例str调用intern()方法,Java 查找常量池中是否有相同Unicode的字符串常量,Java 查找常量池中 是否有相同

Unicode的字符串常量,如果有,则返回其的引用,如果没有,则在常 量池中增加一个Unicode等于str的字符串#并返回它的引用#。
  String s2=new String("abc");
  s2=s2.intern(); //把常量池中"abc"的引用赋给s2,#赋值后才生效# 

***equals()和等号'=='

  1.equals比较两字符串的Unicode序列是否相当,如果相等返回true。
  2.而==是比较两字符串的地址是否相同,也就是是否是同一个字符串的引用。  

***String的不可变性

  因为String的”不可变”,所以在字符串拼接的时候,产生了很多临时变量。

所以在字符串进行连接的时候,应该使用StringBuffer。

  Strings are constant; their values cannot be changed after they are created.  

原文链接:深入Java核心 Java内存分配原理精讲(2)  http://developer.51cto.com/art/201009/225071_1.htm

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值