String 字符串浅析

测试环境为 JDK1.8

测试 1

        String s1 = "abc";
        String s2 = "abc";
        System.out.println(s1 == s2);

显示结果为 true。

创建 String 字面量时,虚拟机在编译期间把该字面量放到 字符串常量池 中。创建 s2 所代表的 “abc” 时,首先检查常量池中是否已经存在相同的字面量(此处已经存在 s1 代表的 “abc” 了),如果存在直接返回该字面量的引用,否则创建新的字符串。所以 s2 和 s1 是同样的引用,完全相等。

如下图所示:

在这里插入图片描述

测试 2

        String s1 = "abc";
        String s2 = new String("abc");
        System.out.println(s1 == s2);
        System.out.println(s1.equals(s2));

显示结果为 false, true。

“new String(“abc”)” 首先在字符串常量池中创建字面量 “abc”(此处由于 s1 已经创建过了,所以不会再重复创建),然后在堆中创建 String 对象。所以这一句话将会让字符串常量池和 堆内存 中都有 “abc”。

s1 持有字符串常量池中的 “abc” 的引用,s2 持有堆中的引用(堆中不保留“abc”,只保留引用),显然不在同一内存中,所以使用 “==” 比较时结果为 false。使用 “equals” 方法只比较它们的值,所以返回 true。

如下图所示:

在这里插入图片描述

测试 3

        String s1 = "ab";
        String s2 = "a" + "b";
        String s3 = "a" + new String("b");
        System.out.println(s1 == s2);
        System.out.println(s1 == s3);

显示结果为 true, false。

s2 由两个字符串常量连接而成,s2 也是字符串常量,在编译器就能确定,直接存在字符串常量池中。
s3 由堆中的字符串对象 “b” 生成,s3 也是对象,直接存在堆内存中。完成后回收堆中的 “b”。

如下图所示:

在这里插入图片描述

测试 4

        String s1 = new String("a");
        String intern1 = s1.intern();
        System.out.println(s1 == intern1);

显示结果为 false。

当调用intern方法时,如果字符串常量池中已经包含与 equals 方法确定的相当于此String 对象的字符串,则返回来自常量池的字符串。 否则,将此 String 对象添加到池中,并返回对常量池中此 String 对象的引用。

如下图所示:

在这里插入图片描述

测试 5

        String s1 = new String("a") + new String("b");
        String intern1 = s1.intern();
        System.out.println(s1 == intern1);
        String s2 = "ab";
        System.out.println(intern1 == s2);

首先在常量池中创建 “a” 和 “b”,然后在堆中创建 “ab”,并将 s1 指向堆中该对象。由于常量池中没有 “ab”,调用 intern 函数返回堆里的 “ab” 对象的地址,并将其添加到常量池中。最后 s2 指向常量池中该对象。

如下图所示:

在这里插入图片描述

对于上面程序中的加号:
若 + 号前后为常量,编译期会处理。
若 + 号前后存在着变量,首先以最左边的字符串为参数创建 StringBuilder 对象,然后依次对右边进行 append 操作,最后将 StringBuilder 对象通过 toString() 方法转换成 String 对象。

参考

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值