当前页面: 开发资料首页 → Netbeans 专题 → NetBeans IDE 4.1/5.0 Profiler 教程
NetBeans IDE 4.1/5.0 Profiler 教程
摘要: NetBeans IDE 4.1/5.0 Profiler 教程 作者及整理人: Gregg Sporar '); //--> Gregg Sporar Gregg Sporar 、 Ruth Kus...
NetBeans IDE 4.1/5.0 Profiler 教程
本文章旨在介绍配合使用 NetBeans Profiler v5.0 或 Profiler Milestone 8 的内容。如果您使用的是 Milestone 5,请使用此版本。如果您使用的是 Milestone 6,请使用此版本。
预计持续时间:50 分钟
NetBeans Profiler 是一个功能强大的工具,它提供了有关应用程序运行时行为的重要信息。NetBeans Profiler 产生的开销相对来说较小,它可以跟踪线程状态、CPU 性能和内存使用情况。本教程将向您介绍如何使用 NetBeans Profiler 来完成以下操作:
- 监视应用程序的运行时行为,其中包括:
- 堆内存大小
- 垃圾回收统计信息
- 线程计数
- 线程状态:运行、休眠、等待、受阻
- 确定应用程序方法使用的 CPU 时间
- 监视应用程序创建对象的过程
先决条件
本教程假定您已经具有了一些基本的 Java 编程和 NetBeans IDE 使用经验。
教程所需的软件:
本文档使用的表示法
- <NETBEANS_HOME> - NetBeans IDE 安装目录
- <USER_HOME> - 用户的 home 目录
- <tutorial_root> - 解压缩教程 zip 文件所在的目录
- 本文档使用 <tutorial_root> 来表示解压缩此教程的 zip 文件所在的目录。此教程的 zip 文件的名称为 profilertutorial.zip。
- 将教程 zip 文件解压缩到 <tutorial_root> 目录时,系统会创建一个名为 netbeansprofiler 的子目录。例如,在 Windows 操作系统中,如果已将教程 zip 文件解压缩到驱动器 E:\ 的根目录中,则系统会创建 E:\netbeansprofiler 子目录。在 Solaris/Linux 操作系统中,如果已将教程 zip 文件解压缩到 /home/username 目录中,则系统会创建 /home/username/netbeansprofiler 子目录。
教程练习
参考资源:
练习 0:安装并配置教程环境
在开始学习教程之前,请先检查以下内容:
- 启动 NetBeans IDE,并确认 IDE 已打开。通过选择 Profile > Help > About Profiler...,验证是否安装了 NetBeans Profiler
。
- 在 Windows 操作系统中,双击 NetBeans IDE 图标
- 在 Solaris/Linux 操作系统中,打开终端窗口,然后键入 <NETBEANS_HOME>/bin/netbeans
- 仅限 NetBeans IDE v4.1:安装所需的修补程序。
- 从 Tools 菜单选择 Update Center,以访问 NetBeans 更新中心。
- 确保选中了 NetBeans Hotfix Update Center,然后单击 Next 按钮。建立连接后,将显示一个更新列表。
- 在 NetBeans Hotfix Update Center 条目下,选择 "NetBeans Profiler (J2EE Projects - Tomcat5 Support)"。该操作还将自动选择 "Tomcat 5 Server" 条目。
- 单击 Next(下一步) 按钮,并按照说明进行操作以便 IDE 可以安装这些修补程序。
练习 1:监视 Swing 应用程序中的线程状态(15 分钟)
本练习的学习目的:
在本练习中,您将学习如何使用 NetBeans Profiler 监视 J2SE 应用程序中的线程状态。这样,您就可以诊断样例应用程序中的性能问题。
背景信息:
Swing 为 J2SE 应用程序提供了图形用户界面组件。Swing 库会使用到多个线程,利用 NetBeans Profiler 这一功能强大的工具,您可以分析出每个线程所花费的处理时间,从而利用这些分析信息来解决性能问题。
执行步骤:
- 选择 File > Open Project。找到 <tutorial_root>/netbeansprofiler/exercises 文件夹。选择 exercise1 文件夹,然后单击 Open Project Folder 按钮。
- 在 Projects() 窗口中,右键单击 exercise1 条目并选择 Clean and Build Project。然后,再次右键单击 exercise1 条目并选择 Run Project。此时,将显示该程序的窗口,如下所示。

- 将 Seconds Before Notification 设置为 30。
- 单击 Start! 按钮。请注意,该程序无法正确地刷新屏幕。
- 单击 Exit 按钮。请注意,该程序根本不会作出响应。
- 将另一个窗口放在该窗口的某一部分上,以遮挡该窗口的视图。当移开另一个窗口时,您会注意到样例应用程序没有相应地刷新其窗口。如下面的示例所示。

- 30 秒后,最终将显示一个消息框,如下所示。单击消息框上的 OK 按钮。

- 应用程序窗口将再次开始响应。单击 Exit 按钮将其关闭。
- 选择 Profile > Profile Main Project。
- 如果出现一个对话框,询问您是否允许修改项目生成脚本,请单击 OK。如下面的示例所示。

- 将会显示 Profile 对话框。单击占据较大区域的 Monitor Application 按钮。
- 应选中 Enable Threads Monitoring 复选框。
- 单击 Run 按钮。如果显示一个对话框,指示您必须先收集 Profiler 的校准信息,请单击 OK 按钮。如下面的示例所示。

选择 Profile > Advanced Commands > Run Profiler Calibration。完成校准后,Profiler 会显示一个对话框,请单击 OK 按钮。如下面的示例所示。

要进行性能分析,请返回至上面的第 9 步。
- 完成上述步骤后,将启动该应用程序,并且 IDE 会显示 Profiler 控制面板,如下所示。

- Profiler 将在其主窗口中显示线程状态,如下面的示例所示。

它使用颜色编码来显示线程状态。
- 绿色:线程正在运行或准备运行。
- 紫色:线程正在调用 Thread.sleep(),处于休眠状态。
- 黄色:线程正在调用 Object.wait(),处于等待状态。
- 红色:线程在尝试访问同步的块或方法时受阻。
- 找到样例 Swing 应用程序的窗口(NetBeans IDE 窗口可能在其上面)。单击样例应用程序中的 Start! 按钮,同时监视标记为 AWT-EventQueue-0 的线程所发生的变化。它将变为绿色并持续这种状态整整 30 秒钟,如以下样例所示。
此图形显示了应用程序没有响应的原因。标记为 AWT-EventQueue-0 的线程是 Swing 用来处理窗口事件的事件分发线程 (Event Dispatch Thread, EDT)。在正常运行的 Swing 应用程序中,EDT 的大部分时间处于等待状态而运行的时间却很少,因为它只有在分发事件时才会运行很短的一段时间。但是,如果应用程序中的事件处理程序未立即返回,则程序将停止响应,就像在此示例中一样。
- 30 秒后,屏幕将显示应用程序的消息框。找到该消息框(NetBeans IDE 窗口可能在其上面)并单击 OK 按钮。然后,单击样例应用程序的 Exit 按钮,将其关闭。
- Projects 窗口与 Profiler 控制面板共享同一个空间;单击 Projects 标签将会显示 Projects 窗口。
- 在 Projects 窗口中,双击 exercise1 条目以将其展开,然后展开 Source Packages 和 profilingthreads 条目。右键单击 DisplayForm.java 条目并选择 Open。
- 在包含 DisplayForm.java 的编辑器窗口中,取消第 132 行至第 157 行的代码块注释。提示:如果未将编辑器配置为显示行号,请选择 View > Show Line Numbers。
- 在包含 DisplayForm.java 的编辑器窗口中,取消(或注释掉)第 122 行到第 128 行的代码块注释。下图突出显示了取消注释的代码块。

- 选择 File > Save。您刚才删除了未正确使用 EDT 的代码,并利用了更稳定可靠的解决方案来替代它。现在,应用程序可以及时地作出响应。
- 选择 Build > Build Main Project(或按 F11 键)。
- 选择 Profile > Profile Main Project。
- 将会显示 Profile 对话框。单击占据较大区域的 Monitor Application 按钮。
- 确保选中了 Enable Threads Monitoring。
- 单击 Run 按钮。
- 当显示样例程序时,单击 Start! 按钮。请注意,此时的性能分析线程图已经发生了变化,如以下示例所示。
EDT 为黄色,应用程序创建的名为“Our SwingWorker #1”的线程为绿色。由于 EDT 不是用来执行耗时任务的,因此,按钮和其他程序控件仍保持响应的状态。
- 在样例程序中单击 Exit 按钮。
- 右键单击 Profiler 图形中的 AWT-EventQueue-0 线程,然后选择 Thread Details。Profiler 会显示一个饼图,表明了每种状态所花的时间;如以下示例所示。
该图形可以帮助您判断程序在每个线程中所花费的时间是否恰当。上述示例是代码修复后的示例,因此,它显示了 EDT 在大部分时间中都处于等待状态的情形,这正好是该线程应具有的行为。
- 在 Projects 窗口中,右键单击 exercise1 条目,然后选择 Close Project。
小结:
在本练习中,您学习了如何使用 Profiler 来启动应用程序,以及如何解释 Profiler 的线程信息图形,以此来跟踪 Swing 应用程序中的性能问题。
返回页首
练习 2:确定某个方法使用的 CPU 时间(15 分钟)
本练习的学习目的:
在本练习中,您将学习如何使用 Profiler 来确定某个应用程序的方法所花费的时间。
背景信息:
CPU 的性能问题通常与应用程序的特定功能有关。例如,在报告系统中,某个报告的运行速度可能比其他报告慢。只分析应用程序中出现性能问题的部分,可以大大减少 Profiler 产生的开销。在本练习中,您将使用 NetBeans Profiler 来检查 Web 应用程序中 CPU 的使用情况。在练习 3 中,我们仍然使用该样例 Web 应用程序来说明如何通过 Profiler 查找内存泄漏。
执行步骤:
- 选择 File > Open Project。找到 <tutorial_root>/netbeansprofiler/exercises 文件夹。选择 exercise2 文件夹,并确保选中 Open As Main Project。单击 Open Project Folder 按钮。
- 在 Projects 窗口中,单击 exercise2 条目,然后从菜单中选择 Build > Clean and Build Main Project。
- 从菜单中选择 Profile > Profile Main Project。如果出现一个对话框,询问您是否允许修改项目生成脚本,请单击 OK。
- 将会显示 Select Profiling Task 对话框。
- 单击 Analyze Performance 按钮。
- 选择 Part of Application 单选按钮。然后,单击位于 Part of Application 单选按钮旁边的 Select 按钮。此时将显示 Specify Root Methods 窗口。
注意:下面的三个步骤仅适用于 Milestone 8。
- 在 Specify Root Methods 窗口中,单击 Add 按钮以添加要分析的根方法。将会显示 Select Method 窗口。
- 在 Select Methods 窗口中,单击 Select 按钮。Profiler 将显示 Go To Class 窗口。
- 在 Class Name 文本字段中输入
Per
。等待 IDE 为您显示适用的类列表。选择 Performance 类。单击 Open 按钮打开其方法列表。
注意:下面的两个步骤只适用于 Profiler v5.0。
- 在 Specify Root Methods(指定根方法) 窗口中,单击 Add From Project...按钮以添加要分析的根方法。将会显示 Select Methods 窗口。
- 在 Class Name 文本字段中,键入 demo.Performance,然后按 Enter 键。
返回页首
分析对象创建过程以查找内存泄漏(20 分钟)
本练习的学习目的:
作为练习 2 的后续练习,我们将在本练习中学习如何解释某些监视应用程序创建对象过程的 Profiler 图形。下面将显示一个内存泄漏示例。
执行步骤:
- 本练习是在练习 2 的基础上进行的,因此,请务必遵循练习 2 中的步骤。
- 从菜单中选择 Profile > Profile Main Project。如果出现一个对话框,询问您是否要停止当前的 Profiler 进程以启动新进程(如下所示),请单击 Yes 按钮继续执行。
将会显示 Select Profiling Task 对话框。
- 在 Select Profiling Task 对话框中,单击占据较大区域的 Monitor Application 按钮。
- 单击 Run 按钮。IDE 将会左侧显示 Profiler 控制台。单击
按钮,或者选择 Profile > View > Telemetry Overview。NetBeans Profiler 将在底部的输出窗口中显示三个图形,如下所示。
在左侧的图形中,红色的阴影部分表示分配的 JVM 堆大小。紫色的覆盖部分表示实际使用的堆空间大小。在上面的示例中,上次更新所分配的堆大小已超过了 20 MB。其中,实际用来保存 Java 对象的堆大小略大于 10 MB。
右侧图形显示了 JVM 中的活动线程数。
中间的图形显示了两种重要的堆统计信息。
- 蓝线是 JVM 执行垃圾回收的时间占执行时间的百分比,它是以图形右侧上的 Y 轴为参照绘制的。JVM 执行垃圾回收所花的时间不能用来运行应用程序。因此,如果蓝线占据较大的百分比,则需要考虑调整 JVM,方法是:配置更大的堆大小(请参阅 -Xmx 参数文档),或者转换到不同的垃圾回收算法中。
-
红线表示存活的生成数,它是以图形左侧的 Y 轴为参照进行绘制的。存活生成数是指 JVM 堆上所有 Java 对象不同生存期的数量,其中“生存期”被定义为对象存活时的垃圾回收次数。如果存活生成数的值较小,则表明堆上的大部分对象的存活时间基本相同。但是,如果存活生成数的值随着时间的变化而增长到一个很高的比率,则表明应用程序正在分配新的对象,同时保持对已分配的多个旧对象的引用。如果实际上不再需要这些旧对象,则应用程序正在浪费(或“泄漏”)内存。
- Profiler 可以对 CPU 性能或内存使用情况进行详细的分析(也称为测试),但不能同时进行这两种分析。要了解有关在 JVM 堆上分配对象以及执行对象的垃圾回收的详细信息,请修改 Profiler 的设置。单击
按钮,或者选择 Profile > Modify Profiling。
- 单击 Analyze Memory Usage 按钮。
- 选择 Record both object creation and garbage collection 单选按钮。
- 选中 Record Stack Trace for Allocations 复选框。
- 单击 OK 按钮。
- 现在,您已经选择了分析内存使用情况,您需要运行应用程序以确定它是否有效地使用了内存。单击 Memory Leak 转至 MemoryLeak 演示页。
- 在 MemoryLeak 演示页上,单击 Start Leaking。
- 请注意存活生成数图形中的峰值,如以下示例所示。这表明可能出现了内存泄漏。
- 选择 Profile > View > Live Results。Profiler 将显示 JVM 堆中分配的对象的动态视图。默认情况下,它将按每个类的所有实例使用的字节数进行排序。由于怀疑可能出现了内存泄漏,因此,请单击 Generations 列,按每个类的不同对象生存期数量对显示结果进行排序。下面显示了得到的显示结果示例。
这些列提供了对象分配和内存使用情况信息。
- Allocated Objects 是 Profiler 正在监视的对象数。在本示例中,共监视了 38 个 float[] 实例。默认情况下,该数字约为应用程序实际分配的对象数的 10%。通过只监视已创建对象的一部分,Profiler 可以显著地减少它在 JVM 中的开销,这样,应用程序就几乎可以按最快的速度运行了。
- Live Objects 是仍在 JVM 堆中并因此占用内存的已分配对象数。
- 两个 Live Bytes 列显示了活动对象所占用的堆内存量。一个列显示图形,另一个列显示文本。
- Avg.Age 值是使用活动对象计算的。每个对象的生存期是它存活时的垃圾回收次数。生存期总和除以活动对象数得到的结果就是 Avg.Age。
- Generations 值是使用 Live Object 计算的。与 Avg.Age 相同,对象生存期是它存活时的垃圾回收次数。Generations 值是活动对象的不同生存期数量。
- 随着程序继续运行,Profiler 将更新显示结果。请留意 float[] 和 double[] 条目。请注意其生成数值是如何持续增加的。结果是,float[] 和 double[] 在列表中持续上移。最终,它们会显示在列表的顶部,紧靠 java.util.HashMap$Entry(其生代数值也在不断增加)下方。随着应用程序继续运行,java.util.HashMap$Entry、float[] 和 double[] Generations 值持续增加,但任何其他类没有增加。如下面的示例所示。
- 要了解导致 Generations 值持续增加的原因,请选择 Profile > Take Snapshot of Collected Results。按 Generations 对显示结果进行排序。右键单击 double[] 条目,然后选择 Show Allocation Stack Traces。Profiler 将显示所有分配了一个或多个 double[] 对象的方法。如下面的示例所示。
请注意,在分配了 double[] 对象的方法中,只有一个方法创建了具有较大 Generations 值的 double[] 对象。该方法是 run(),它位于具有相应名称 demo.memoryleak.LeakThread 的类中。
- 右键单击 run() 方法条目,然后选择 Go To Source...。Profiler 将显示源代码,如下所示。
请注意,正在分配 double[] 和 float[] 对象,并随后将其放在 HashMap 中。但一直并未删除它们,这意味着,HashMap 保留的引用将会妨碍 JVM 对这些对象进行垃圾回收。这是非常典型的 Java 内存泄漏:将对象放在 Map 中,然后就忘记处理它们了。由于本示例中使用的 Map 就是 HashMap,因此,关联的 java.util.HashMap$Entry 对象也出现了泄漏。
- 选择 Profile > Stop 来结束性能分析会话,或者单击
按钮。
- 在 Projects 窗口中,选择 exercise2 条目,然后从菜单中选择 File > Close Project。
小结:
在本练习中,您学习了如何使用 Profiler 来监视应用程序创建对象的过程。您还看到了 Profiler 在应用程序出现内存泄漏时所提供的各种类型的分析指数。
返回页首
恭喜您!您已成功地完成了 NetBeans IDE 4.x Profiler 教程。
↑返回目录
前一篇:
NetBeans Profiler 功能
后一篇:
使用 NetBeans IDE 5.0 开发 Struts Web 框架的快速入门指南