printf( )

Table of contents:


I was inspired to write the first edition of this book by the numerous questions I received about why there was no printf( ) function in Java. Part of the goal of that edition was to explain to readers why they didn't actually need it. Thus, I was a little perturbed when Java 5 added printf( ). Personally, I still don't think Java needs printf( ), but it's here now, so let's talk about it.

The printf( ) method makes heavy use of Java 5's new varargs feature. That is, a single method definition can support any number of arguments. In this case, the signature is:

public PrintStream printf(String format, Object... args)

A typical invocation looks like this:

System.out.printf("There are %f centimeters in %f inches.", 2.54*inches, inches);

If you're an old C hack, this is like coming home. The first argument is a format string containing both literal text and tags beginning with percent signs (%). To form the output, each tag is replaced by the corresponding argument that follows the format string. If the format string is the zeroth argument, the first tag is replaced by the first argument, the second tag by the second argument, and so forth. If there are more tags than arguments, printf( ) tHRows a java.util.MissingFormatArgumentException. This is a subclass of IllegalFormatException, which is a runtime exception, so you don't have to catch it. If there are more arguments than tags, the extra arguments are silently ignored.

The letter(s) after the percent sign in the format tag specify how the number is interpreted. For instance, %f means that the number is formatted as a floating-point number with a decimal sign. %d formats the argument as a decimal integer. %x formats the number as a hexadecimal integer. %X also formats the number as a hexadecimal integer but uses the uppercase letters A-F instead of the lowercase letters a-f to represent 10-15.

Most of the time, changing a lowercase conversion specifier to uppercase changes the formatted string from lowercase to uppercase. However, there are a few exceptions to this rule.

There are a couple of dozen tags for different kinds of data. Not all data is compatible. For instance, if you use %x to format a double as a hexadecimal integer, printf( ) throws a java.util.IllegalFormatConversionException. Again, this is a runtime exception and a subclass of IllegalFormatException.

So far, this isn't anything that can't be done easily with println( ) and string concatenation. What makes printf( ) more convenient for some uses is that the tags can also contain width and precision specifiers. For example, suppose we wrote the previous statement like this instead:

System.out.printf("There are %.3f centimeters in %.2f feet.", 2.54*feet, feet);

%.3f means that the centimeters will be formatted as a decimal number with exactly three digits after the decimal point. %.2f means that the number will be rounded to only two decimal places. This gives more legible output, like "There are 21.691 centimeters in 8.54 feet" instead of "There are 21.690925 centimeters in 8.539734 feet."

A number before the decimal point in the format tag specifies the minimum width of the formatted string. For instance, %7.3f formats a decimal number exactly seven characters wide with exactly three digits after the decimal point. Those seven characters include the decimal point, so there will be exactly three digits to the left of the decimal point. If the number is smaller than 100, it will be padded on the left with spaces to make seven characters. Zeros will be added to the right of the decimal point if necessary to pad it to three decimal places.

Consider this Java 1.4 code fragment that prints a three-column table of the angles between 0 and 360 degrees in degrees, radians, and grads, using only println( ):

for (double degrees = 0.0; degrees < 360.0; degrees++) {
 double radians = Math.PI * degrees / 180.0;
 double grads = 400 * degrees / 360;
 System.out.println(degrees + " " + radians + " " + grads);

Its output looks like this (not very pretty):

0.0 0.0 0.0
1.0 0.017453292519943295 1.1111111111111112
2.0 0.03490658503988659 2.2222222222222223
3.0 0.05235987755982988 3.3333333333333335

In Java 5, printf( ) can easily format each number exactly five characters wide with one digit after the decimal point:

for (double degrees = 0.0; degrees < 360.0; degrees++) {
 double radians = Math.PI * degrees / 180.0;
 double grads = 400 * degrees / 360;
 System.out.printf("%5.1f %5.1f %5.1f
", degrees , radians, grads);

Here's the start of the output:

0.0 0.0 0.0
1.0 0.0 1.1
2.0 0.0 2.2
3.0 0.1 3.3

Notice how nicely everything lines up in a monospaced font? This is incredibly useful for the two dozen programmers using Java to generate reports for VT-100 terminals and letter-quality printouts on green-and-white barred computer paper. (Those readers who haven't written any software like that since 1984, and certainly those readers who weren't even born in 1984, should now see why I'm less than thrilled with the addition of this 1970s technology to a 21st-century language.)

Of course, programmers printing text in proportional-width fonts, GUI table components, HTML reports, XML documents styled with XSL stylesheets, and any other output format produced since 1992 may be less enamored of this style of programming. Anyway, Java has it now. You don't have to use it (or read the rest of this chapter) if you don't need it.

Basic I/O

Introducing I/O

Output Streams

Input Streams

Data Sources

File Streams

Network Streams

Filter Streams

Filter Streams

Print Streams

Data Streams

Streams in Memory

Compressing Streams

JAR Archives

Cryptographic Streams

Object Serialization

New I/O



Nonblocking I/O

The File System

Working with Files

File Dialogs and Choosers


Character Sets and Unicode

Readers and Writers

Formatted I/O with java.text


The Java Communications API


The J2ME Generic Connection Framework


Character Sets

Java I/O
Java I/O
ISBN: 0596527500
EAN: 2147483647
Year: 2004
Pages: 244 © 2008-2020.
If you may any questions please contact us: