有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java如何为StringBuffer(“+”+“+”)分配内存

String将始终创建新的内存空间,而StringBuffer不会,每当我们附加新值时,它将更新现有内存

我的问题是:假设,我使用

new StringBuffer("A " + "B " + "C " + "D " + "E " + "F").toString();  

内存分配是如何完成的


共 (2) 个答案

  1. # 1 楼答案

    如果没有@Neerav所描述的特例优化(因此在较旧的JRE中,或者如果没有文字字符串),代码最终会带来大量CPU和内存开销

    表达式是"A " + "B " + "C " + "D " + "E " + "F"。这意味着(没有优化)

    new StringBuilder("A ").append("B ").append("C ").append("D ")
        .append("E ").append("F").toString()
    

    在执行代码行时,像"A "这样的文本字符串不会被分配。加载类时,它们会被预先分配到字符串池中

    您的代码创建一个StringBuilder(现代替代StringBuffer)并将字符附加到其缓冲区。因此,它分配StringBuilder基本对象和一个字符数组。可能初始缓冲区不够大,然后在某个时刻StringBuilder必须分配一个新的、更大的数组,将字符从旧数组复制到新数组,然后继续

    最后,表达式需要是String而不是StringBuilder,因此得到toString()。这将创建一个新的String基对象和一个大小完全正确的新字符数组

    然后将这个表达式包装在new StringBuffer(...).toString()中,这是完全不必要的。首先,这将创建一个新的StringBuffer基对象加上一个足够大的新字符数组,并将字符复制到那里。然后在这个StringBuffer上调用toString(),它创建另一个String基实例加字符数组,并再次将字符复制到这个新的String对象中。在new StringBuffer(...).toString()之前,您已经有了一个完全相同的String

    所以,你分配:

    • 1 StringBuilder
    • 两条线
    • 1字符串缓冲区
    • 包括4个字符数组(如果StringBuilder的初始大小不够,可能会更多)
  2. # 2 楼答案

    Java编译器足够聪明,可以在编译时连接字符串ABCDEF,并将其作为编译时常量加载。。因此,池中只会创建一个字符串