测量Java程序的最大驻留集大小

时间:2015-12-27 21:29:07

标签: java

我需要比较在C,C ++和Java中执行时相同算法的内存消耗。在做了一些阅读后,我发现测量最大驻留集大小是内存消耗的最佳指标。对于C / C ++,我可以使用getrusage()来获取数据,但对于Java,我无法找到任何等价物。

3 个答案:

答案 0 :(得分:2)

比较Java和C / C ++之间的内存使用情况很困难。虽然最大驻留集大小(RSS)等度量在C / C ++中是有意义的,但它们不是Java。

  • 在C / C ++中,最大RSS是最大内存使用量的一个很好的近似值。

  • 在Java中,任何时间点的RSS都可能包含当前拥有垃圾和可用空间的堆的部分内容。此外,最大的RSS将受到您选择的垃圾收集参数的强烈影响。 GC人机工程学的工作方式意味着对于堆大小(减少GC开销)而言,一个好主意是慷慨的。但这意味着你的最大RSS会更大。

另一方面,最大RSS并不是C / C ++程序中内存使用量的完美衡量标准:

  • "居民"在RSS中意味着系统正在计算物理内存页面而不是虚拟页面。如果系统物理内存不足,则应用程序的非共享虚拟内存使用量(这是您真正需要测量的内容)可能远远大于最大RSS。

  • 如果您的C / C ++应用程序正在使用malloc内存,并且它反复进行mallocing和释放,那么您可能会获得大量的堆碎片并且这会使最大RSS值膨胀

最后,如果您确实想尝试在Java中使用getrusage,那么执行此操作的方法是编写一个小的本机代码过程来进行调用,并通过JNI或JNA调用该过程。 / p>

答案 1 :(得分:0)

JMX是通常的方式从内部从Java应用程序获取这些统计信息。 How do I access memory usage programmatically via JMX?

Interface MemoryMXBean文档。

这为你提供了关于虚拟内存的堆,但是它应该接近RSS,因为你将从当前的JVM中获取。除非您使用JNI / JNA / JNR以非跨平台的方式调用getrusage()。

E.g以下示例使用JNA for Closure,(另一种JVM语言,类似应该与Java一起使用) https://github.com/circleci/clj-getrusage

答案 2 :(得分:-1)

或许this tutorial可能对您有用,或the MemoryUsage Class。

来自教程:

public class PerformanceTest {
  private static final long MEGABYTE = 1024L * 1024L;

  public static long bytesToMegabytes(long bytes) {
    return bytes / MEGABYTE;
  }

  public static void main(String[] args) {
    // I assume you will know how to create a object Person yourself...
    List<Person> list = new ArrayList<Person>();
    for (int i = 0; i <= 100000; i++) {
      list.add(new Person("Jim", "Knopf"));
    }
    // Get the Java runtime
    Runtime runtime = Runtime.getRuntime();
    // Run the garbage collector
    runtime.gc();
    // Calculate the used memory
    long memory = runtime.totalMemory() - runtime.freeMemory();
    System.out.println("Used memory is bytes: " + memory);
    System.out.println("Used memory is megabytes: "
        + bytesToMegabytes(memory));
  }
} 

MemoryUsage对象描述:

  

MemoryUsage对象表示内存使用情况的快照。实例   MemoryUsage类通常由方法构造   用于获取有关各个内存池的内存使用信息   Java虚拟机或Java的堆或非堆内存   虚拟机整体。 MemoryUsage对象包含四个值:

     
      
  • init 表示Java的初始内存量(以字节为单位)   虚拟机从操作系统请求内存   启动期间的管理。 Java虚拟机可能会请求   来自操作系统的额外内存,也可能会释放   随着时间的推移对系统的记忆。 init的值可能未定义。
  •   
  • use 表示当前使用的内存量(以字节为单位)。   committed表示内存量(以字节为单位)   保证可供Java虚拟机使用。该   提交的内存量可能随时间而变化(增加或   减少)。 Java虚拟机可能会向系统释放内存   并且承诺可能少于init。
  • 已提交将永远是   大于或等于使用。
  • max 表示最大金额   可用于内存管理的内存(以字节为单位)。它的价值   可能是未定义的。如果,最大内存量可能会随时间而变化   定义。已使用和已提交的内存量将始终较少   如果定义了max,则大于或等于max。内存分配可能会失败   如果它试图增加使用的内存,那么使用&gt;提交   即使用过