Most people will already be familiar with profiling, but you might be less aware of the different types of profilers on offer. A recent issue we had upon the release of Java 8 proved awkward to resolve using a traditional profiler, but Sampling proved well suited to the task.
Helpfully, Java comes with both a traditional profiler and a sampler in the form of VisualVM. I’m just going to be talking about CPU profiling, although the approaches to memory are similar.
VisualVM’s profiler works by “instrumenting” all of the methods of your code. This adds extra bytecode to your methods for recording when they’re called, and how long they take to execute each time they are.
VisualVM’s sampler, however, takes a dump of all of the threads of execution on a fairly regular basis, and uses this to work out how roughly how much CPU time each method spends.
So what was our problem with profiling?
We test our software by running our PDF to HTML5 converter on a large number of diverse PDF files which make use of different parts of the PDF specification and flagging up any changes in the output. On Java 8, this was taking 48 minutes.
One problem with instrumented profiling is that it adds a constant amount of extra execution time to every single method call. Sometimes – such as in image processing – small, quick methods are called many, many times, adding a great deal of time to the execution. Profiling our tests this way would take hours!
Sampling, however, takes a more or less constant amount of time each second to record stack traces for each thread. This only added 5 – 10 minutes of execution time in total, and still provided us with a good idea of where the problems lay.
One quirk of sampling is that the number of invocations recorded is not necessarily accurate, since a short method could easily start and finish between stack dumps. It appeared as though a method in our library was called three times as often in Java 8 as it was in Java 7 – the truth, however, is that it was taking three times as long, and thus was three times as likely to be caught in a dump.
Perhaps the lesson here is that sampling is most useful for recording the amount of CPU time spent, rather than the number of invocations. Still, there’s a very high chance that this will identify any problems, and do it much faster than the standard profiler.
Which do you prefer? Let us know in the comments below.
Are you a Developer working with PDF files?
Our developers guide contains a large number of technical posts to help you understand the PDF file Format.
Do you need to solve any of these problems?
|Display PDF documents in a Web app|
|Use PDF Forms in a web browser|
|Convert PDF Documents to an image|
|Work with PDF Documents in Java|
8 Replies to “Profiling Vs. Sampling in Java’s VisualVM”
Very well said on above issue. However we have option to use either of them. This feature was lacking in previous java profilers and now included ?
JProfiler has had some sampling options since at least 2011 so it’s definitely not unique to JProfiler. I don’t know who did it first, but it’s certainly a useful alternative to instrumented profiling.
I am using VisualVM Sampler for profiling the application. On right corner there us button to hide / unhide columns. There I selected ‘Samples’ column. Now I can see for some methods the value in this column is 32 and for some column the value is just 1. So to get accurate time taken by a given method should time be divided by Samples?
This would provide you with an approximate time taken by the method – an accurate time will not be achievable with sampling. Samples tells you how many invocations have been observed, which for short methods is very likely to be many fewer than actually occurred.
One issue with the sampler is that you can’t profile specific classes when sampling Memory :(. Is that right?
That does seem to be correct, yes.
Memory sampling just periodically displays a classes histogram produced by the JVM. It’s low-overhead by its nature and there’s no benefit in limiting the scope to just specific classes. You can always use the results filter to hide the classes of no interest.
like we can see how much memory our class will take in jvisualvm , is it possible to see this thing for Fun as well?
if yes , then HOW