java - 如何测量java方法的内存使用情况

标签 java performance jvm

听起来很奇怪,但仍然如此。

假设我有一个 java 方法

boolean myMethod(Object param1, Object param2) { 
   // here can be some simple calculations. can be some services invokation
   // or calls to DB. doesn't matter
  return someValue;
}

如何测量 JVM 使用多少内存来执行此方法?该方法的执行实际使用了多少内存?

是否有任何工具,或者我可以在我的方法中添加一些额外的代码以便能够查看已使用的内存?

我正在使用JConsole要监控JVM,我也知道我们可以使用java.lang.Runtime查看 freeMemory,但实际上我无法计算出我的方法使用此工具使用了多少内存。

最佳答案

测量方法每次调用的真实大小并不像听起来那么简单,而且 JVM 也不支持它。复杂性的产生是 a) 因为 JVM 的设计目的是隐藏这种低级细节,b) JVM 可能在任何时间点都有多个相同方法的变体,这听起来很疯狂,但也是事实。有时,该方法将被内联,或者进行更严格的优化,甚至以特殊方式重新编译,以支持该方法在运行时热交换(!),这可以从根本上改变其运行时大小。

测量方法调用使用的堆量

鉴于方法调用不使用堆,很容易说 0 字节。然而,人们可能想知道通过方法调用分配的任何新对象的大小。这是可以回答的,但是对象是在方法调用和线程之间共享的。因此,人们必须非常清楚自己想要衡量什么,并注意不要重复计算。有一些库可以给出 Java 中对象的大小,它们通常通过反射和启发式工作,或者包装 sun.misc.Unsafe 来检查指向对象及其数据的指针。例如http://code.google.com/p/javabi-sizeof/ .

测量方法的分配率

YourKit 有一个出色的工具,描述 here用于跟踪源点的每个对象分配并报告其总大小和速率。对于找出谁导致 GC 流失非常有用。

测量每个方法调用使用的堆栈量

JVM 不会发布此信息,并且如前所述,它将根据当前 Activity 的优化以及正在使用的运行时编译器而有所不同。

另一种方法是使用启发式方法。比如计算方法中使用了多少个变量,然后将计数乘以 4,得到以字节为单位的答案(假设每个变量的大小为 4 个字节,即 int)。显然,这种启发式方法是有缺陷的,可以改进,但它足够简单,可以给出快速且相当有代表性的答案。

关于java - 如何测量java方法的内存使用情况,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26055745/

相关文章:

java - 安装 SOAP UI 后出现 JVM 错误

linux - 如何确定 Linux 上多进程的 JVM 内存占用

Java 桌面应用程序

Julia 中 for 循环的性能

java - FreeMarker编码困惑

r - 当已知可能的输出时加速 `strsplit`

python - 为什么我的 python 打印比 Go 的 fmt.Print 和 os.Stdout.Write 运行得更快

java - 线程优先级算法的正确性

java - 如何表示垂直的 showOptionDialog 按钮

java - 我是否有重新排序问题,是否由于引用转义?