19.8 Performance Tuning

Java Servlet Programming, 2nd Edition > 19. Odds and Ends > 19.8 Performance Tuning

 
< BACKCONTINUE >

19.8 Performance Tuning

Performance tuning servlets requires a slightly different mindset than performance tuning normal Java applications or applets. The reason is that the JVM running the servlets is expected to simultaneously handle dozens, if not hundreds, of threads, each executing a servlet. These coexisting servlets have to share the resources of the JVM in a way that normal applications do not. The traditional performance-tuning tricks still apply, of course, but they have a different impact when used in a heavily multithreaded system. What follows are some of the tricks that have the largest special impact on servlet developers.

19.8.1 Go Forth, but Don't Prosper

Avoid the unnecessary creation of objects. This has always been good advice creating unnecessary objects wastes memory and wastes a fair amount of time as the objects are created. With servlets, it's even better advice. Traditionally many JVMs have used a global object heap that must be locked for each new memory allocation. While any servlet is creating a new object or allocating additional memory, no other servlet can do so.

19.8.2 Don't Append by Concatenation

Avoid concatenating several strings together. Use the append( ) method of StringBuffer instead. This too has always been good advice, but with servlets it's particularly tempting to write code like this to prepare a string for later output:

String output; output += "<TITLE>"; output += "Hello, " + user; output += "</TITLE>";

Although this code looks nice and neat, when it runs it executes as if written roughly as follows, with a new StringBuffer and new String created on each line:

String output; output = new StringBuffer().append("<TITLE>").toString(); output = new StringBuffer(output).append("Hello, ").toString(); output = new StringBuffer(output).append(user).toString(); output = new StringBuffer(output).append("</TITLE>").toString();

When efficiency counts, rewrite the original code to look like the following, so just one StringBuffer and one String are created:

StringBuffer buf = new StringBuffer(); buf.append("<TITLE>"); buf.append("Hello, ").append(user); buf.append("</TITLE); output = buf.toString();

Note that using an array of bytes is even more efficient.

19.8.3 Limit Synchronization

Synchronize whenever necessary, but no more. Every synchronized block in a servlet slows the servlet's response time. Because the same servlet instance may handle multiple concurrent requests, it must, of course, take care to protect its class and instance variables with synchronized blocks. All the time one request thread is in a servlet's synchronized block, however, no other thread can enter the block. Therefore, it's generally best to keep these blocks as small as possible.

You should also take a look at the worst-case result of thread contention. If the worst case is bearable (as with the counter example from Chapter 3), you can consider removing synchronization blocks entirely. Also consider using the SingleThreadModel tag interface, where the server manages a pool of servlet instances to guarantee each instance is used at most by one thread at a time. Servlets that implement SingleThreadModel don't need to synchronize access to their instance variables.

Finally, remember that java.util.Vector and java.util.Hashtable are always internally synchronized, while the equivalent java.util.ArrayList and java.util.HashMap, introduced in JDK 1.2, are not synchronized unless requested. So if your Vector or Hashtable doesn't need synchronization and you're running on JDK 1.2, try the unsynchronized ArrayList or HashMap instead.

19.8.4 Buffer Your Input and Output

Buffer your input and your output, all your storage files, any streams loaded from a database, and so on. This almost always improves performance, but the improvement can be especially profound with servlets. The reason is reading and writing one unit at a time can slow down the entire server due to the frequent context switches that have to be made. Fortunately, you generally don't need to buffer when writing to a servlet's PrintWriter or ServletOutputStream or when reading from a servlet's BufferedReader or ServletInputStream. Most server implementations already buffer these streams.

19.8.5 Try Using an OutputStream

For web pages using the Latin-1 character encoding, it's technically possible to use either a PrintWriter or a ServletOutputStream to write to the client. Using a PrintWriter is the recommended approach because it supports internationalization, but on some servers using a ServletOutputStream provides a noticeable performance increase, and ServletOutputStream conveniently has a long list of print( ) and println( ) methods left over from Servlet API 1.0 when there was no PrintWriter option. Just be careful. Many servers are just the opposite and with them using a PrintWriter provides higher performance. Unless you're sure of your deployment platform and have run comparable time trials, stick with PrintWriter.

19.8.6 Use a Profiling Tool

There are a number of Java profiling tools available that can help identify bottlenecks in your code. After all, most performance problems in server-side Java are caused not by the language or JVM but rather by a handful of bottlenecks; the trick is locating those bottlenecks. These analysis tools run in the background, observing as your web server handles requests, reporting a detailed summary of where time was spent as well as how memory was allocated. Two popular tools are OptimizeIt! from Intuitive Systems (http://www.optimizeit.com) and JProbe from Sitraka, formerly the KL Group (http://www.sitraka.com/jprobe). Many JVMs also accept command-line flags (-prof under JDK 1.1 and -Xrunhprof under JDK 1.2) to report some basic profiling information. To run the server under load you can use a tool such as Apache JMeter (http://java.apache.org/jmeter).


Last updated on 3/20/2003
Java Servlet Programming, 2nd Edition, © 2001 O'Reilly

< BACKCONTINUE >


Java servlet programming
Java Servlet Programming (Java Series)
ISBN: 0596000405
EAN: 2147483647
Year: 2000
Pages: 223

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net