【问题标题】:Detect low memory in Java?检测Java中的低内存?
【发布时间】:2017-12-18 14:32:03
【问题描述】:

为了防止出现OutOfMemoryError,我想创建一个代码,在存在超出可用 RAM 的危险时清除程序中的一些缓存。

当内存处于可用最大值的一定百分比时,我如何从代码内部检测到并能够做出反应?

【问题讨论】:

  • 你不能/不应该。实现缓存时使用 SoftReference。
  • 如何在缓存中使用软/弱引用,如果需要更多空间,垃圾收集器会自动清除它们?
  • 检查空闲内存的部分问题在于,它只告诉你一个数字。您仍然不知道如何填充 JVM 内存部分的足够详细信息(可能会有很大不同,具体取决于您对垃圾收集器的选择和设置)。所以,你不知道你的特定瓶颈到底在哪里。因此,最好采用 Michael 和 Marco13 推荐的更简洁的设计。
  • @AskarIbragimov 对不起,如果你觉得我会给你贴上初级标签,那绝不是我的本意——我只是想问评论者,如果他们给一些规则之类的建议(“你不应该......”),也分享这种教条背后的推理

标签: java memory-management out-of-memory


【解决方案1】:

事实证明(令我惊讶!)有一种半可靠的方法可以检测内存使用量是否超过预设阈值。

MemoryPoolMXBean 类提供了一种方法来设置内存池的使用阈值,并在池的使用量超过阈值时收到通知。

您可以通过调用 ManagementFactory.getMemoryPoolMXBeans() 来获取 JVM 的内存 MXBean 实例。

有两种阈值,你需要了解它们之间的区别才能正确使用它们。比较复杂:参考javadoc

还需要注意的是规范:

  • 说不是所有的空间都支持阈值检查,
  • 表示对何时测试阈值交叉没有限制:

    “Java 虚拟机在其最佳适当时间基于内存池执行使用阈值交叉检查...”

  • 说明如何测试是否支持阈值检查,以及如何注册通知。

【讨论】:

    【解决方案2】:

    检测 Java 中的内存消耗以对您的代码做出反应并不是一个好主意。你永远不知道垃圾收集器的行为方式、启动时间、启动频率、可以释放多少内存……

    如果您想防止对对象的引用阻止垃圾收集器将其删除,则可以使用 Wea​​kReference (java.lang.ref)。但是如果你实现了一个缓存,这可能会使缓存变得无用,因为你的缓存对象可能会被非常快速且频繁地删除。

    我建议使用 LRU-Cache。这样的缓存具有一定的容量。如果超过此容量,最近最少使用的元素将被踢出缓存。这以一种简单的方式防止您的缓存可以无限增长。

    如果你google一下,你可以找到一些简单的实现:

    public class LRUMap<K, V>  extends LinkedHashMap<K, V> {
        private static final long serialVersionUID = 1L;
        private final int capacity;
    
        public LRUMap(final int capacity) {
            this.capacity = capacity;
        }
    
        @Override
        protected boolean removeEldestEntry(Map.Entry<K, V> eldest) {
            return size() > capacity;
        }
    }
    

    如果您需要更多,我会检查现有的缓存实现。它们可能支持其他配置功能,例如 e. G. 缓存条目的最大年龄。

    【讨论】:

    • 我们实际上有一个有限的缓存,但如果内存不足,我可以将这个限制转移到更少的值。只需要找出内存实际上是低的。
    • 我真的怀疑这是否可以以可靠的方式完成。您可以尝试使用 Runtime.getRuntime().totalMemory() 和 Runtime.getRuntime().maxMemory() 来指示当前内存使用量是否已达到极限。
    猜你喜欢
    • 2011-10-08
    • 2015-11-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-02-15
    • 2017-04-14
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多