如何以非交互方式分析 Java 应用程序?

Posted

技术标签:

【中文标题】如何以非交互方式分析 Java 应用程序?【英文标题】:How can I profile a Java application non-interactively? 【发布时间】:2013-07-02 19:46:38 【问题描述】:

我想做的是在 Java 应用程序执行脚本任务时生成一个包含 CPU 计时信息的调用树。我们的想法是查看代码的每个部分花费了多少时间,以及当我更改代码或任务时这会如何变化,但要以一致可重复的方式进行。

在 Java VisualVM 中,我可以通过单击开始和停止分析来交互地执行此操作,但我想自动化该过程,以便获得更一致的结果(并且不会那么无聊)。 VisualVM 可以做到这一点,还是有其他分析器可以做到这一点?

【问题讨论】:

YourKit 允许您在特定的代码行开始和停止分析。 @PeterLawrey:NetBeans 分析器也允许这样做。但我猜 Ben 不想在 IDE(或分析器)中运行应用程序 谢谢。我将研究 YourKit 和 NetBeans。 (我通常使用 Eclipse 作为 IDE。)我不太介意如何运行应用程序,只要我能让它每次都执行相同的步骤。 【参考方案1】:

如果我是分析器供应商,我将不得不关心为人们提供他们认为他们想要的东西,即使他们认为他们想要的东西并不能解决他们遇到的问题。

问题是,只有知道例程通常需要多长时间才能发现一些问题,如果你忽略那些你没有找到的问题,它们将成为你的程序需要多少时间的主要部分。

我的意思的一个例子是最近的例子: 程序花费 50% 的挂钟时间读取 .dll 文件以查找字符串资源以获取文件名,以便将字符串显示在启动屏幕上,以便用户可以看到应用程序启动期间正在发生的事情。这意味着,如果有其他方式可以让用户眼前一亮,应用程序的启动速度可能会提高一倍。 在这个过程中,调用堆栈的深度通常为 15-20 个函数,因此仅通过函数的计时数字很难判断发生了什么。

问题的难点在于它是语义。没有一个特定的例程是“热”的,它可以被加速。 唯一“热门”的事情是总体上对程序正在做什么的一般描述,没有工具可以为您隔离它。 只有你能认出来。

但是,如果您只是在启动期间中断程序并检查调用堆栈,那么您有 50% 的可能性会看到所花费时间的全部解释。 如果你多次这样做,它就是random pausing technique 的基础,一些程序员依赖它,因为它会发现分析器可以找到的所有问题,以及更多,而其他人则看不起它,因为它不是工具。

并以交互方式执行此操作,或者使用类似于 pstack 的方法提取少量堆栈样本。

【讨论】:

Java VisualVM 可以使用采样,这实际上(我认为)与随机暂停相同,但会自动重复多次。但无论是通过检测类进行采样还是分析,我都希望在更改代码时快速查看结果中的差异,而不是重复繁琐的手动过程。这有意义吗? @Ben:不同之处不在于采样,而在于对其进行总结。分析远比时间精度有用。要查看更改的效果,对我来说简单的时间就足够了。为了找出要修复的内容,与暂停相比,分析器的工作效果不佳。与暂停不同,使用它们的实际加速结果很难在线找到。 Here's 43x.至于繁琐,我可以给你看一些链接,比如this one

以上是关于如何以非交互方式分析 Java 应用程序?的主要内容,如果未能解决你的问题,请参考以下文章

如何以非交互方式在 Git 中重新排序提交

以非交互方式执行 rgrep

使用 git 以非交互方式编辑旧提交

有没有办法以非交互方式压缩大量提交?

仅当函数的返回值等于“Value”时,gdb 是不是可以在函数上以非交互方式有条件地中断?

仅在以非交互方式运行 bash 脚本时出现错误“cat: write error: Broken pipe”