字符串连接和内存泄漏

Viv*_*vek 0 java

我们几乎到处都使用串联字符串进行日志记录.
例如:catch (Exception e) { logger.error("setUserSession()" + e.getMessage()); } 但我们怀疑这些语句是否因字符串变异而导致内存泄漏.有人建议使用String builder.但是我从Java中的toString()中的StringBuilder vs String连接等讨论中理解的是Java Compiler将使用String builder来转换字符串连接.

为了测试这个,我试图反编译以下java代码(使用JD-GUI);

    logger.error("string1" + "string2");
    logger.error("setUserSession()" + e.getMessage());
Run Code Online (Sandbox Code Playgroud)

而反编译器产生以下代码;

    logger.error("string1string2");
    logger.error("setUserSession()" + e.getMessage());
Run Code Online (Sandbox Code Playgroud)

但是我期待第二个语句中的String builder就像;

logger.error(new StringBuilder().append("setUserSession()").append(e.getMessage());
Run Code Online (Sandbox Code Playgroud)

所以我有两个疑问:

  1. 字符串连接实际上是否会造成如此多的内存泄漏?
  2. 或者我是否需要明确地使用字符串构建器 - >将我的字符串附加到字符串构建器 - >然后使用字符串构建器删除功能删除字符串构建器?
  3. Java编译器使用"字符串"构建器转换简单字符串连接.(我们可以使用反编译工具来检查吗?)

Tim*_*m B 6

  1. 它不会造成内存泄漏.它将创建内存使用,但垃圾收集器将整理它.
  2. StringBuilder除非您的字符串连接分布在多个语句中,否则无需显式使用.
  3. 是.

我认为你对Java有一个误解.不要紧,这些对象是否为String,Object,MyObject或其他任何东西.只要对它的所有强引用都超出范围,对象就有资格进行垃圾收集,并在适当的时候回收使用的内存.

在Java中泄漏内存的唯一方法是泄漏资源(例如打开流,创建线程等)或者意外地保留对某些内容的引用(例如将其添加到List并且永远不会从List中删除它).