• 字符串,引用变量与常量池


    Reference:

    [1] http://www.cnblogs.com/langtianya/p/3868135.html

    [2] http://www.cnblogs.com/timecloud/p/6555868.html

    1. 引用变量

    根据上下文来确定存放位置:
    比如
    void func()
    {
        Object obj = new Object();//这个obj在函数的栈里。
    }

    class Test
    {
       private Object obj = new Object();//这个obj随对应的Test对象分配在堆里
    }

    2. 常量池(constant pool)

    指的是在编译期被确定,并被保存在已编译的.class文件中的一些数据。它包括了关于类、方法、接口等中的常量,也包括字符串常量。

    常量: 代表程序运行过程中不能改变的值。在Java语法中,常量也可以首先声明,然后再进行赋值,但是只能赋值一次。

     java中的 final变量==常量

    2. String

    String a = "abc";
    该语句创建对象的过程:先在常量池中查找是否有内容为"abc"的字符串对象,若有,直接将该对象的引用赋给a;若没有,则在常量池中创建"abc"对象,再将其引用赋给a。

    String a1 = new String("abc");
    String a2 = new String("abc");
    在常量池没有"abc"对象的前提下,这两条语句产生了3个对象,两个处于堆中的string对象,一个处于字符串常量池string对象。

    String a1 = "abc";
    String a2 = "abc";
    在常量池没有"abc"对象的前提下,这两条语句产生了一个对象,位于字符串常量池中。当String a1 = "abc"执行完毕后,JVM会在字符串常量池中创建一个"abc"对象;然后执行String a2 = "abc"时会先在常量池中查询是否有"abc",如果有,将"abc"的引用赋给a2;如果没有,在在字符串常量池中创建一个"abc"对象,再赋给a2。

    String a1 = new String("abc");
    String a2 = new String("abc");
    String a3 = "abc";
    String a4 = "abc";
    在常量池没有"abc"对象的前提下,这四条语句一共创建了三个对象。String a1 = new String("abc")分别在堆和常量池中创建了"abc"对象,然后String a2 = new String("abc")也在堆中创建了"abc"对象,String a3 = "abc"和String a4 = "abc"都是从常量池中获取"abc"的引用。

    String b1 = "abc";
    String b2 = "ab";
    String b3 = "ab" + "c";
    String b4 = b2 + "c";
    其中b1 = b3 ? true;b1 = b4 ? false。String b3 = "ab" + "c"会直接在常量池中查找"abc"对象,若存在,直接引用该对象。
    而String b4 = b2 + "c"会生成新的对象,其内部实现是先new一个StringBuilder,然后 append(b2),append("c");然后让b4引用toString()返回的对象。

    String s = "aa" + "bb"这种形式是先将两个字符串拼接起来,再在常量池中查找拼接过后的字符串对象("aabb");
    String s1 = "aa";String s2 = s1 + "bb";这种形式是生成新的对象,这个对象内部实现是先new一个StringBuilder,
    然后 append(s1),append("bb");然后让s2引用toString()返回的对象。

    public String intern()
    返回字符串对象的规范化表示形式。 一个初始为空的字符串池,它由类 String 私有地维护。 
    当调用 intern 方法时,如果池已经包含一个等于此 String 对象的字符串(用 equals(Object) 方法确定),则返回池中的字符串。否则,将此 String 对象添加到池中,并返回此 String 对象的引用。 
    它遵循以下规则:对于任意两个字符串 s 和 t,当且仅当 s.equals(t) 为 true 时,s.intern() == t.intern() 才为 true。 所有字面值字符串和字符串赋值常量表达式都使用 intern 方法进行操作。返回:

    一个字符串,内容与此字符串相同,但一定取自具有唯一字符串的池。
    例:
    String str1 = "abbb"; 
    String str2 = new String("abbb").intern(); 
    System.out.println(str1==str2); //true

  • 相关阅读:
    正确理解原型和原型链
    git push之后服务器如何自动更新?
    项目工具三:Swagger导出离线版HTML5和PDF格式api文档
    项目工具二:通过SQL导出单表的结构文档
    项目工具一:把文件夹里所有子文件夹与文件按树形结构导出
    一个完整的HTTP请求过程详细
    SAAS多租户数据逻辑隔离
    JS同步执行代码
    提升JAVA代码的好“味道”
    Connection keepalive
  • 原文地址:https://www.cnblogs.com/codingforum/p/6904551.html
Copyright © 2020-2023  润新知