OutputStream is an abstract class that mainly describes the operations available with any OutputStream object. Specific subclasses know how to write bytes to particular destinations. For instance, a FileOutputStream uses native code to write data in files. A ByteArrayOutputStream uses pure Java to write its output in an expanding byte array.
Recall that there are three overloaded variants of the write( ) method in OutputStream, one abstract, two concrete:
public abstract void write(int b) throws IOException public void write(byte[] data) throws IOException public void write(byte[] data, int offset, int length) throws IOException
Subclasses must implement the abstract write(int b) method. They often also override the third variant, write(byte[], data int offset, int length), to improve performance. The implementation of the three-argument version of the write( ) method in OutputStream simply invokes write(int b) repeatedlythat is:
public void write(byte[] data, int offset, int length) throws IOException { for (int i = offset; i < offset+length; i++) write(data[i]); }
Most subclasses can provide a more efficient implementation of this method. The one-argument variant of write( ) merely invokes write(data, 0, data.length); if the three-argument variant has been overridden, this method will perform reasonably well. However, a few subclasses may override it anyway.
Example 2-3 is a simple program called NullOutputStream that mimics the behavior of /dev/null on Unix operating systems. Data written into a null output stream is lost.
Example 2-3. The NullOutputStream class
package com.elharo.io; import java.io.*; public class NullOutputStream extends OutputStream { private boolean closed = false; public void write(int b) throws IOException { if (closed) throw new IOException("Write to closed stream"); } public void write(byte[] data, int offset, int length) throws IOException { if (data == null) throw new NullPointerException("data is null"); if (closed) throw new IOException("Write to closed stream"); } public void close( ) { closed = true; } } |
The no-op flush( ) method inherited from the superclass is good enough here since this stream really doesn't need flushing. However, note that this class does need to check whether the stream is closed before writing anything, and check whether the array passed in to write( ) is null. Most subclasses will need to make similar checks.
By redirecting System.out and System.err to a null output stream in the shipping version of your program, you can disable any debugging messages that might have slipped through quality assurance. For example:
OutputStream out = new NullOutputStream( ); PrintStream ps = new PrintStream(out); System.setOut(ps); System.setErr(ps);
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
Buffers
Channels
Nonblocking I/O
The File System
Working with Files
File Dialogs and Choosers
Text
Character Sets and Unicode
Readers and Writers
Formatted I/O with java.text
Devices
The Java Communications API
USB
The J2ME Generic Connection Framework
Bluetooth
Character Sets