在探索了java的字符串内部结构之后,我对所谓的" perm空间感到困惑。"我最初的理解是它保留了String
文字以及类元数据,如this question中所述。
我还阅读了String.intern()
方法,并将String
放入字符串池中,返回对其唯一实例的引用。我的理解是,这是存在于JVM的perm-space中的String字符串的相同字符串池。对于我而言,“烫发空间”#34;可以修改,(毕竟它是永久性的,是吗?)。但后来我找到了this question,其中EJP对接受的答案的最高投票评论解释了
实习生的字符串已经可以使用GC了很多年了。
暗示GC在perm空间上运行,这似乎不是永久性的。这如何调和? GC是否检查了烫发空间中的所有内容? GC是否检查字符串池中的所有内容,包括源中的字符串文字?实习生的字符串是否有第二个字符串池? GC是否只知道在收集时查看实习生的字符串?或者这个评论是错误的,并且实际上是一个字符串会阻止它成为GC' d(我希望不是这样)?
答案 0 :(得分:9)
字符串文字are interned。从Java 7开始,HotSpot JVM将实际的字符串放入堆中,而不是permgen。
在java 7之前,hotspot将perings中的字符串放入。但是,interned Strings in permgen were garbage collected。显然,Class objects in permgen are also collectable,因此permgen中的所有内容都是可收集的,但默认情况下可能不会在某些旧JVM中启用permgen集合。
正在实习的字符串文字将是由声明的Class对象保留在实习池中的String对象所持有的引用。因此,只有在收集引用它的Class对象时,才会收集实习的文字字符串。