【问题标题】:What is the difference between PermGen and Metaspace?PermGen 和 Metaspace 有什么区别?
【发布时间】:2015-01-23 17:15:49
【问题描述】:

在 Java 7 之前,JVM 内存中有一个名为 PermGen 的区域,JVM 曾经在其中保存其类。在Java 8 中,它被移除并替换为名为Metaspace 的区域。

PermGen 和 Metaspace 之间最重要的区别是什么?

我知道的唯一区别是java.lang.OutOfMemoryError: PermGen space 不能再被抛出,VM 参数MaxPermSize 被忽略。

【问题讨论】:

  • 第一个谷歌结果:infoq.com/articles/Java-PERMGEN-Removed
  • @the8472 是的,但是这个(和许多其他的)谷歌结果只描述了元空间机制,没有提到这个和 PermGen 之间的确切区别。

标签: java java-8 java-7 permgen metaspace


【解决方案1】:

从用户角度来看的主要区别 - 我认为前面的答案不够强调 - 默认情况下元空间会自动增加它的大小(直到底层操作系统提供的大小),而 PermGen总是有一个固定的最大尺寸。您可以使用 JVM 参数为 Metaspace 设置一个固定的最大值,但不能使 PermGen 自动增加。

在很大程度上,这只是名称的改变。早在引入 PermGen 时,没有 Java EE 或动态类(卸载)加载,因此一旦加载了一个类,它就会卡在内存中,直到 JVM 关闭 - 因此 Permanent 生成。现在类可能在 JVM 的生命周期内被加载和卸载,因此 Metaspace 对于保存元数据的区域更有意义。

它们都包含java.lang.Class 实例,它们都受ClassLoader leaks 的影响。唯一的区别是,使用 Metaspace 默认设置,您需要更长的时间才能注意到症状(因为它会自动增加尽可能多),即您只是将问题推得更远而不解决它。 OTOH,我想 OS 内存耗尽的影响可能比 JVM PermGen 耗尽的影响更严重,所以我不确定这是否是一个很大的改进。

无论您是使用带有 PermGen 或 Metaspace 的 JVM,如果您正在执行动态类卸载,您应该采取措施防止类加载器泄漏,例如使用我的 ClassLoader Leak Prevention library

【讨论】:

  • Permgen 和 Metaspace 都不包含 Class 类的实例。它们只保留有关已加载类的元信息。类 Class 的实例保存在常规堆中,就像其他类的实例一样。
  • 不错的比较。谢谢
  • 顺便说一句,OTOH 的意思是“另一方面”
【解决方案2】:

再见,再见 PermGen,你好元空间

PermGen 已被完全删除。

元空间垃圾回收 - 一旦类元数据使用达到MaxMetaspaceSize,就会触发死类和类加载器的垃圾回收。

Metadata 被占用的空间不再与 Java heap 连续,metadata 现在已移至本机内存中称为 Metaspace 的区域。

简单来说

由于类元数据是从本机内存分配的,因此最大可用空间是总可用系统内存。因此,您将不会再遇到OOM errors 并且最终可能会溢出到交换空间中。

删除PermGen 并不意味着您的类加载器泄漏问题消失了。所以,是的,你仍然需要监控你的消耗并做出相应的计划,因为泄漏最终会消耗你的整个本机内存。

其他一些文章,有分析:Link1, Link2, and this

【讨论】:

  • 你有 MaxMetaspaceSize 而不是 MaxPermGen,所以没有理由它会使用更多或更少的内存或者你有更少的控制。
  • 我们在这里谈论的是什么内存? RAM 内存或 HDD 内存。
  • @Dinesh RAM(内部存储器)
  • OOM => “内存不足”
【解决方案3】:

简而言之,如果不受 -XX:MaxMetaspaceSize 限制,元空间大小会根据需要在本机内存中自动增加以加载类元数据

【讨论】:

    【解决方案4】:

    这里是为了简单。

    什么是永久代: PermGen 是与主内存堆分离的特殊堆空间。类元数据在此处加载。 java 7:PermGen 是 JVM 跟踪已加载类的元数据的空间。
    java 8 : PermGen 被 Metaspace 取代,具有根据加载类元数据的要求自动增加本机内存的能力。

    【讨论】:

      【解决方案5】:

      永久代

      • (永久代)是与主内存分离的特殊堆空间。
      • JVM 跟踪 PermGen 中的类元数据。 此外,JVM 将所有静态内容存储在此中。
      • 由于内存大小有限,PermGen 可能会抛出 OutOfMemoryError。

      元空间

      • 元空间是一种新的内存空间。
      • 它已经取代了旧的 PermGen 内存空间。
      • 它现在可以处理内存分配。
      • 默认情况下,元空间会自动增长。

      【讨论】:

        猜你喜欢
        • 2014-07-27
        • 2010-10-02
        • 2011-12-12
        • 2010-09-16
        • 2012-03-14
        • 2012-02-06
        • 2011-02-25
        • 2011-11-22
        • 2015-03-26
        相关资源
        最近更新 更多