[ Team LiB ] Previous Section Next Section

Simple Java Optimizations

In addition to optimizing the performance of your servlet engine by manipulating the threads, or increasing throughput by modifying the buffering, you can do many simple things in your Java code to speed it up. These optimizations are always useful, whether you're writing a Web application, a GUI application, or an applet.

Use the StringBuffer Class

This is a very basic Java performance issue that applies just as much to JavaServer Pages. Many Java programmers never take the time to use the StringBuffer class. Some programmers, who should know better, frequently ignore it even in situations in which it should be used. Most programmers concatenate two strings with a statement like this:


String foobar = "foo" + "bar";

When you look at this statement, you naturally assume that the Java Virtual Machine must have some built-in string concatenation operation. What most people don't realize, however, is that the Java compiler generates code similar to this:


StringBuffer a = new StringBuffer("foo");
a.append("bar");
foobar = a.toString();

Creating one string buffer isn't so bad, but things slow down when you have a series of concatenations, like this:


String name = prefix;
name = name + " "+firstName ;
name = name + " "+middleName;
name = name + " "+lastName;
name = name + " "+suffix;

Each new assignment creates a new StringBuffer object. When you execute this code many times, you start creating a lot of StringBuffer objects. You are much better off creating a single StringBuffer object yourself and appending the strings to it, like this:


StringBuffer nameBuff = new StringBuffer(prefix);
nameBuff.append(" ");
nameBuff.append(firstName);
nameBuff.append(" ");
nameBuff.append(middleName);
nameBuff.append(" ");
nameBuff.append(lastName);
nameBuff.append(" ");
nameBuff.append(suffix);
String name = nameBuff.toString();

When you need to optimize your programs, start looking for places where you use + to concatenate strings. If you do several concatenations, replace them with StringBuffer and you'll see a reasonable performance increase.

Parsing Numbers

When you need to convert a string into a number, you use the various object wrapper classes, such as Integer, Double, Long, and so on. There are several ways to convert a string into a number when using these classes, but there is only one optimal way (assuming that you want a native type as the end result).

When you want to convert a string into an int, for example, you might use one of the two following statements:


int i = (new Integer("12345")).intValue();
int i = Integer.valueOf("12345").intValue();

The problem with both these statements is that they create a new Integer object first and then extract the int value from the object. The most efficient way to convert a string into an int is by the parseInt method:


int i = Integer.parseInt("12345");

In fact, both the string constructor for Integer and Integer.valueOf use parseInt to first create an int and then wrap an Integer object around it. The other classes have their own parse methods, such as parseDouble and parseLong.

Creating Objects

As you might have noticed, the previous two optimization tips centered around reducing the number of objects you create. Object creation consumes time and memory, and the fewer times you do it, the faster your program runs. In fact, with a good just-in-time compiler, a Java program that doesn't create any objects can run about as fast as a C program that doesn't allocate memory. For example, Java programs that analyze chess moves recursively and reuse the same memory for the board tend to run at about the same speed as their C counterparts. Although situations like this are rare in a typical business application, you can see that object creation does contribute to the relative slowness of Java.

    [ Team LiB ] Previous Section Next Section