常用JavaProfiling工具的分析与比较在Java程序的开发过程中,不可避免地会遇到内存使用、性能瓶颈等问题。JavaProfiler工具能帮助开发人员快速、有效地定位这些问题,因此成为了Java开发过程中的一个重要工具。目前市场上的JavaProfiler工具种类繁多,本文将对目前比较常见的几种工具进行简要介绍,并从功能、性能等角度作比较,从而帮助Java程序员选择合适的JavaProfiler工具。本文主要分为三个部分:第一部分简要介绍JavaProfiler工具的原理;第二部分对目前常见的JavaProfiler工具TPTP,CodeProProfiler,YourKitJavaProfiler,JProfiler进行简要介绍;第三部分对以上工具从不同的角度进行比较,帮助开发人员选择合适的工具。内容相对于静态代码分析,Profiling是通过收集程序运行时的信息来研究程序行为的动态分析方法。其目的在于定位程序需要被优化的部分,从而提高程序的运行速度或是内存使用效率。收集程序运行时信息的方法主要有以下三种:事件方法:对于Java,可以采用JVMTI(JVMToolsInterface)API来捕捉诸如方法调用、类载入、类卸载、进入/离开线程等事件,然后基于这些事件进行程序行为的分析。统计抽样方法(sampling):该方法每隔一段时间调用系统中断,然后收集当前的调用栈(callstack)信息,记录调用栈中出现的函数及这些函数的调用结构,基于这些信息得到函数的调用关系图及每个函数的CPU使用信息。由于调用栈的信息是每隔一段时间来获取的,因此不是非常精确的,但由于该方法对目标程序的干涉比较少,目标程序的运行速度几乎不受影响。植入附加指令方法(BCI):该方法在目标程序中插入指令代码,这些指令代码将记录profiling所需的信息,包括运行时间、计数器的值等,从而给出一个较为精确的内存使用情况、函数调用关系及函数的CPU使用信息。该方法对程序执行速度会有一定的影响,因此给出的程序执行时间有可能不准确。但是该方法在统计程序的运行轨迹方面有一定的优势。目前市面上的JavaProfiler工具采用的信息收集方法通常是以上三种方法的任意组合。Profiler工具功能简介虽然市场上的JavaProfiler工具有不少,但是基本功能大多相似,本节首先对这些基本功能进行介绍。遥测(Telemetry):遥测是一种用来查看应用程序运行行为的最简单的方法。通常会有多个视图(View)分别实时地显示CPU使用情况、内存使用情况、线程状态以及其他一些有用的信息,以便用户能很快地发现问题的关键所在。oCPUTelemetry视图一般用于显示整个应用程序的CPU使用情况,有些工具还能显示应用程序中每个线程的CPU使用情况。oMemoryTelemetry视图一般用于显示堆内存和非堆内存的分配和使用情况。oGarbageCollectionTelemetry视图显示了JVM中垃圾收集器的详细信息。oThreadsTelemetry视图一般用于显示当前运行线程的个数、守护进程的个数等信息。oClassesTelemetry视图一般用于显示已经载入和还没有载入的类的数量。快照(snapshot):应用程序启动后,profiler工具开始收集各种执行数据,其中一些数据直接显示在遥测视图中,而另外大部分数据被保存在内部,直到用户要求获取快照,基于这些保存的数据的统计信息才被显示出来。快照包含了应用程序在一段时间内的执行信息,通常有两种类型的快照:CPU快照和内存快照。oCPU快照主要包含了应用程序中函数的调用关系及运行时间,这些信息通常可以在CPU快照视图中进行查看。o内存快照则主要包含了内存的分配和使用情况、载入的所有类、存在的对象信息及对象间的引用关系。这些信息通常可以在内存快照视图中进行查看。CPUProfiling:CPUProfiling的主要目的是统计函数的调用情况及执行时间,或者更简单的情况就是统计应用程序的CPU使用情况。通常有两种方式来显示CPUProfiling结果:CPU遥测和CPU快照。内存Profiling:内存Profiling的主要目的是通过统计内存使用情况检测可能存在的内存泄露问题及确定优化内存使用的方向。通常有两种方式来显示内存Profiling结果:内存遥测和内存快照线程Profiling:线程Profiling主要用于在多线程应用程序中确定内存的问题所在。一般包括三个方面的信息:o某个线程的状态变化情况o死锁情况o某个线程在线程生命期内状态的分布情况Profiling的启动设置:类似于eclipse中Run和Debug的启动设置,进行Profiling之前也需要进行启动设置,包括:profiling的模式(CPUprofiling或内存profiling),信息获取类型(遥测,抽样统计或者BCI)等等。ProfilerPreference设置:主要用于Profiler过滤器(选择需要关注的包、类)、取样间隔时间的设置等。JavaProfiler工具介绍本文接下来将对目前市场上常见的几种JavaProfiler工具进行介绍。TPTPTPTP(TestandPerformanceToolsPlatform)是eclipse官方的Profiling工具插件。TPTP提供了诸如测试,追踪(trace),性能测试,图形界面性能分析等功能。同时TPTP还是一个可扩展的开发平台框架,你可以对它加以扩展集成到你自己的产品中。TPTP可以通过EclipseupdateManager或者是安装包进行安装,安装成功后会在eclipse中增加如下所示的按钮,另外一个专门的用于检查TPTPprofiling结果的perspective也会添加进eclipse中,如下图所示:图1.TPTPCodeProProfilerCodeProProfiler是由instantiations公司推出的一款商用eclipse插件,它可以通过EclipseupdateManager进行安装或者是将安装包直接解压缩后保存在eclipse的指定目录下。与TPTP类似,安装成功后,有一个专门的用于查看CodeProprofiling结果的perspective会添加进eclipse中,如下图所示:图2.CodeProYourKitProfilerYourKitJavaProfiler也是一款商用软件,支持的操作系统包括:Windows,Linux,FreeBSD,MacOSX,Solaris以及HP-UX;支持的IDE包括:Eclipse,JBuilder,JDeveloper,NetBeans以及IntellijIDEA。安装成功且首次启动YourKitJavaProfiler后,会弹出一个对话框,让用户选择YourKitJavaProfiler要集成进的IDE,并指定该IDE的安装路径,点击”InstallPlugin”按钮并集成成功之后,Eclipse中会出现如下图标,用户就可以从Eclipse中启动Profiling,但是profiling的结果需要在YourKitJavaProfiler中进行查询,如下图所示:图3.YourKitJProfilerJProfiler是由ej-technologies推出的一款商用软件,支持的操作系统有:Windows,Linux,MacOSX,FreeBSD,Solaris,AIX以及HP-UX;支持的IDE包括:Eclipse,NetBeans,IntellijIDEA,JBuiler以及JDeveloper。安装成功并首次启动JProfiler后,会弹出一个设置界面,当完成左栏所示的那些步骤后,Eclipse中就会出现如下图标,用户就可以从Eclipse中启动Profiling。与YourKitJavaProfiler类似,profiling的结果需要在JProfiler中进行查询,如下图所示:图4.JProfiler回页首JavaProfiler工具比较本章节将从如下几个方面对上述工具进行比较:与Eclipse的集成性oTPTP:是一款基于Eclipse开发的插件,因此与eclipse的集成性很好。安装成功后,对TPTP的一切设置与操控都可以在eclipse中完成;另外,profiling的结果也可以在eclipse中进行查询。oCodeProProfiler:与TPTP类似,CodeProProfiler也是一款基于eclipse开发的插件,因此与eclipse的集成性很好好。用户在eclipse中就可以完成对profiling的所有操作。oYourKitJavaProfiler:YourKitJavaProfiler可以说是一个比较独立的工具,安装成功后,用户可以直接在eclipse中启动YourKitJavaProfiler并对profiling选项进行配置,但是用户必须在YourKitJavaProfiler工具中对Profilingpreferrence进行配置,而且profiling信息必须在YourKitJavaProfiler中进行查看。因此和Eclipse的集成度一般。oJProfiler:JProfiler也是一款比较独立的工具,安装成功后,用户可以直接在eclipse中启动JProfiler,其他所有操作必须回到JProfiler工具中进行。因此和Eclipse的集成性不好。遥测种类oTPTP:目前使用的4.6.2的版本只提供了线程Telemetry。oCodeProProfiler:总共有五个类型:CPU,内存,线程,载入的类以及垃圾收集。oYourKitJavaProfiler:与CodeProProfiler相比,缺少载入类的监测。oJProfiler:与CodeProProfiler一样,总共有五个类型的监测方法。CPU快照包含的统计数据类型oTPTP:CPU快照包含的统计数据有:包的组成关系,细化到包含的类及类中的方法。方法的调用关系:以每个线程为根节点的方法调用信息,对于树中出现的代表方法的每个节点,列出了该方法的运行时间或运行时间百分比,以及该方法被调用的次数。方法被调用情况:列出了直接调用某方法的其他方法,以及这些方法调用该方法的次数及相关运行时间。热点列表:包含了CPU占用时间排列前十的方法、类或包。oCodeProProfiler:CPU快照包含的统计数据类型有:包的组成关系,细化到包含的类及类中的方法。方法的调用关系。以树结构表示,根据根节点表示的对象的不同,分为三种类型:以每个线程为根节点的方法调用关系,以整个线程为根节点的方法调用关系,以及以每个方法为根节点的方法调用关系。对于树中出现的代表方法的每个节点,列出了该方法的运行时间或运行时间百分比,以及由该方法生成的对象个数和为这些对象分配的内存大小。方法的被调用关系。该关系以树结构表示,其中根节点为某个指定的方法,每个节点的子节点为父节点的调用者。热点列表:包含了CPU占用时间排前的一些方法。oYourKitJavaProfiler:CPU快照包含的统计数据类型与CodeProProfiler类似;oJProfiler:与CodeProProfiler相比,缺少以每个方法为根节点的方法调用关系。因此当要查看以某个方法为调用起点的调用关系时,需要到以线程为根的树结构当中去查找。另外,方法的被调用关系不是以树结构来表示的,而是以图的方式来显示的,当调用关系比较复杂的时候,很难在一个屏幕中看到一个全局关系图。内存快照包含的统计数据类型oTPTP:包含了类实例的内存分配情况,包括实例化的对象个数,以及这些对象的本身占用内存的大小。相对于其它JavaProfiler工具,TPTP的内存快照包含的统计数据类型比较少。oCodeProProfiler:包含的统计数据有类实例的内存分配情况,包括实例化的对象个数,以及这些对象的shallow和retained大小。(Shal