【问题标题】:Java Garbage Collection after heap memory crosses a threshold堆内存超过阈值后的 Java 垃圾收集
【发布时间】:2020-07-21 10:02:04
【问题描述】:

每次堆内存超过特定阈值时,是否可以在 java 中调用强制垃圾回收?

【问题讨论】:

  • 我知道这并不过分有用,但也许您应该找出您的应用程序使用这么多内存的原因,然后尽可能减少它,或者提供更多内存。
  • 为什么?这样做有什么意义?你知道什么是 JVM 不知道的,你“更清楚”什么时候需要运行 GC?
  • @Andreas 虽然有点牵强,但是如何生成需要大量时间的报告?您不希望潜在的 Full GC 引入更多时间,因此在报告生成之前触发 Full GC。我想可能还有其他情况 - 因为有些工具实际上可以为您提供这种能力。如果有工具可以做到这一点,我猜肯定会有人需要它。
  • @Eugene 问题不在于在代码中的某个特定 point 触发,例如在报告之前,它已经被支持 (System.gc()),但是关于触发堆内存使用阈值,即在堆为例如时触发完整 GC 30% 满,而不是让 JVM 自己决定何时应该完成部分和完全 GC。所以我问OP有什么意义。为什么这会比 JVM 的内置逻辑有所改进,后者已经过大量测试以进行微调?

标签: java garbage-collection heap-memory java-heap


【解决方案1】:

理论上是的,你可以配置这样的行为。确切的细节取决于使用的垃圾收集算法。例如,对于 CMS,您可以在堆内存使用率达到 70% 时启动 GC。很可能您还想设置初始和最大内存限制。

-XX:+UseConcMarkSweepGC -XX:+UseCMSInitiatingOccupancyOnly -XX:CMSInitiatingOccupancyFraction=70

希望对你有帮助!

【讨论】:

  • CMS 已弃用且已死,仅供参考
【解决方案2】:

已经发生了。例如在G1GC 中,这要么是年轻空间已满(对于次要收集),要么是在InitiatingHeapOccupancyPercent 被命中时(对于主要收集)。这两者都是通过标志控制的,所以你可以知道什么时候确切是应该触发的 GC,如果你真的想要那个。

Shenandoah 中有ShenandoahGCHeuristics 会选择一些启发式方法(它们也取决于大小)。

另一方面,如果您想以编程方式执行此操作(已经有工具可以执行此操作),您可以编写一些代码来检查堆的大小(例如通过ManagementFactory::getMemoryPoolMXBeans),然后 via an agent call。一般来说,您需要一个非常充分的理由来执行此操作。

【讨论】:

  • 感谢您的回复,但未将 InitiatingHeapOccupancyPercent 设置为默认值 45%
  • @Jaharsh 我还有其他号码吗?
猜你喜欢
  • 1970-01-01
  • 2012-06-12
  • 2012-06-28
  • 1970-01-01
  • 1970-01-01
  • 2013-01-24
  • 2013-12-30
  • 2014-03-31
  • 1970-01-01
相关资源
最近更新 更多