不可变和可变字符序列使用陷阱

· String使用的陷阱

String一经初始化后,就不会再改变其内容了。对String字

符串的操作实际上是对其副本(原始拷贝)的操作,原来的字符串一点都没有改变
。比如:

String s ="a"; 创建了一个字符串

s = s+"b"; 实际上原来的a字符串对象已经丢弃了,现在又产生了另一个字符串s+"b"(也就是ab)。 如果多次执行这些改变串内容的操作,会导致大量副本字符串对象存留在内存中,降低效率。如果这样的操作放到循环中,会极大影响程序的时间和空间性能,甚至会造成服务器的崩溃。

相反,StringBuilder和StringBuffer类是对原字符串本身操作的,可以对字符串进行修改而不产生副本拷贝或者产生少量的副本。因此可以在循环中使用。

通过比较运行时对String字符串的地址和StringBuilder可知String字
符串的操作实际上是对其副本(原始拷贝)的操作等同每一次都创建了新的对象;
而StringBuilder和StringBuffer类是对原字符串本身操作的。

【示例】String和StringBuilder在字符串频繁修改时的效率测试
public class Test {
    public static void main(String[ ] args) {
        /**使用String进行字符串的拼接*/
        String str8 = "";
        
        long num1 = Runtime.getRuntime().freeMemory();//获取系统剩余内存空间
        long time1 = System.currentTimeMillis();//获取系统的当前时间
        for (int i = 0; i < 5000; i++) {
            str8 = str8 + i;//相当于产生了5000个对象
        }
        long num2 = Runtime.getRuntime().freeMemory();
        long time2 = System.currentTimeMillis();
        System.out.println("String占用内存 : " + (num1 - num2));
        System.out.println("String占用时间 : " + (time2 - time1));
        /**使用StringBuilder进行字符串的拼接*/
        StringBuilder sb1 = new StringBuilder("");
        long num3 = Runtime.getRuntime().freeMemory();
        long time3 = System.currentTimeMillis();
        for (int i = 0; i < 5000; i++) {
            sb1.append(i);
        }
        long num4 = Runtime.getRuntime().freeMemory();
        long time4 = System.currentTimeMillis();
        System.out.println("StringBuilder占用内存 : " + (num3 - num4));
        System.out.println("StringBuilder占用时间 : " + (time4 - time3));
    }
}

执行结果如图所示:



#java基础知识#
全部评论
见识了
点赞 回复 分享
发布于 2022-10-24 17:58 陕西

相关推荐

04-17 18:32
门头沟学院 Java
野猪不是猪🐗:他跟你一个学校,你要是进来之后待遇比他好,他受得了?
点赞 评论 收藏
分享
只有一个苍穹外卖外加正在看黑马点评,可以找小厂实习吗,还有我的简历有什么大问题吗
Java抽象小篮子:感觉有点熟悉,问题1是学历,2是没实习经历,3是专业技能写得太少太少了(怎么写可以看我置顶帖),4是仅这一个项目找实习不够看。拷打完毕,简历怎么写可以看我置顶帖子
点赞 评论 收藏
分享
评论
1
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务