Java I/O Streams


Serialization and Deserialization

Serialization is the conversion of the state of an object into a byte stream; deserialization is conversion of byte stream into an object. Stated differently, serialization is the conversion of a Java object into a static stream (sequence) of bytes which can then be saved to a database or transferred over a network.

The serialization process is instance-independent, i.e. objects can be serialized on one platform and deserialized on another. Classes that are eligible for serialization need to implement a special marker interface Serializable.


Marker Interface

An interface that does not contain methods, fields, and constants is known as marker interface. In other words, an empty interface is known as marker interface or tag interface. It delivers the run-time type information about an object. It is the reason that the JVM and compiler have additional information about an object. The Serializable and Cloneable interfaces are examples of marker interfaces.

Serializable Interface

Serializable is a marker interface (has no data member and method). It is used to "mark" Java classes so that the objects of these classes may get a certain capability. The Serializable interface must be implemented by the class whose object needs to be persisted.


I/O Stream

In Java streams are the sequence of data that are read from the source and written to the destination.
Input stream is used to read data from the source. Output stream is used to write data to the destination.

Types of Stream
  • Byte Stream
  • Character Stream
java types of stream

Byte Stream
Byte stream is used to read and write a single byte (8 bits) of data. All byte stream class are derived from base abstract classes called InputStream abn OutputStream.
Character Stream
Character strea is used to read and write single character of data. All character stream classes are derived from base abstract classes Reader and Writer.

InputStream

InputStream represents an ordered scequence of bytes. In other words you can read from a java input stream as a orderd sequence of bytes.

java InputStream class

Methods of InputStream

Method Description
read() reads one byte of data from the input stream
read(byte[] array) reads bytes from the stream and stores in the specified array
available() returns the number of bytes available in the input stream
close() closes the input stream

OutputStream

Java application uses an output stream to write data to a destination; it may be a file, an array, peripheral device or socket.

java OutputStream class

Methods of OutputStream

Method Description
write() writes the specified byte to the output stream
write(byte[] array) writes the bytes from the specified array to the output stream
flush() forces to write all data present in output stream to the destination
close() closes the output stream
FileInputStream

Java FileInputStream class obtains input bytes from a file. It is used for reading byte-oriented data (streams of raw bytes) such as image data, audio, video etc.
import java.io.FileInputStream;
import java.io.InputStream;

class Main {
public static void main(String args[]) {
byte[] array = new byte[100];
try {
InputStream input = new FileInputStream("input.txt");
System.out.println("Available bytes in the file: " + input.available());

// Read byte from the input stream
input.read(array);
System.out.println("Data read from the file: ");

// Convert byte array into string
String data = new String(array);
System.out.println(data);

// Close the input stream
input.close();
} catch (Exception e) {
e.getStackTrace();
}
}
}

Output:
Available bytes in the file: 39
Data read from the file:
This is a line of text inside the file

FileOutputStream

FileOutputStream is an outputstream for writing data/streams of raw bytes to file or storing data to file.
import java.io.FileOutputStream;

public class Main {
public static void main(String[] args) {

String data = "This is a line of text inside the file.";
try {
FileOutputStream output = new FileOutputStream("output.txt");
byte[] array = data.getBytes();

// Writes byte to the file
output.write(array);
output.close();

} catch(Exception e) {
e.getStackTrace();
}
}
}
Output:
This is a line of text inside the file


ObjectInputStream

The ObjectInputStream is mainly used to read data written by the ObjectOutputStream. Basically, the ObjectOutputStream converts Java objects into corresponding streams. This is known as serialization. Those converted streams can be stored in files or transferred through networks.
Now, if we need to read those objects, we will use the ObjectInputStream that will convert the streams back to corresponding objects. This is known as deserialization.
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;

class Dog implements Serializable {
String name;
String breed;

public Dog(String name, String breed) {
this.name = name;
this.breed = breed;
}
}

class Main {
public static void main(String[] args) {

// Creates an object of Dog class
Dog dog = new Dog("Tyson", "Labrador");

try {
FileOutputStream file = new FileOutputStream("file.txt");

// Creates an ObjectOutputStream
ObjectOutputStream output = new ObjectOutputStream(file);

// Writes objects to the output stream
output.writeObject(dog);
FileInputStream fileStream = new FileInputStream("file.txt");

// Creates an ObjectInputStream
ObjectInputStream input = new ObjectInputStream(fileStream);

// Reads the objects
Dog newDog = (Dog) input.readObject();
System.out.println("Dog Name: " + newDog.name);
System.out.println("Dog Breed: " + newDog.breed);
output.close();
input.close();

} catch (Exception e) {
e.getStackTrace(); }
}
}
Output:
Dog Name: Tyson
Dog Breed: Labrador

ObjectOutputStream

Basically, the ObjectOutputStream encodes Java objects using the class name and object values. And, hence generates corresponding streams. This process is known as serialization. Those converted streams can be stored in files and can be transferred among networks.


BufferedInputStream

The BufferedInputStream maintains an internal buffer of 8192 bytes.
During the read operation in BufferedInputStream, a chunk of bytes is read from the disk and stored in the internal buffer. And from the internal buffer bytes are read individually.
Hence, the number of communication to the disk is reduced. This is why reading bytes is faster using the BufferedInputStream.
import java.io.BufferedInputStream;
import java.io.FileInputStream;

class Main {

public static void main(String[] args) {
try {
// Creates a FileInputStream
FileInputStream file = new FileInputStream("input.txt");
// Creates a BufferedInputStream
BufferedInputStream input = new BufferedInputStream(file);
// Reads first byte from file
int i = input .read();
while (i != -1) {
System.out.print((char) i);
// Reads next byte from the file
i = input.read(); }

input.close();
}

catch (Exception e) {
e.getStackTrace(); }
}
}
Output:
This is a line of text inside the file.

BufferedOutputStream

The BufferedOutputStream maintains an internal buffer of 8192 bytes.
During the write operation, the bytes are written to the internal buffer instead of the disk. Once the buffer is filled or the stream is closed, the whole buffer is written to the disk.
Hence, the number of communication to the disk is reduced. This is why writing bytes is faster using BufferedOutputStream.
import java.io.FileOutputStream;
import java.io.BufferedOutputStream;

public class Main {
public static void main(String[] args) {
String data = "This is a line of text inside the file";

try {
// Creates a FileOutputStream
FileOutputStream file = new FileOutputStream("output.txt");
// Creates a BufferedOutputStream
BufferedOutputStream output = new BufferedOutputStream(file);
byte[] array = data.getBytes();
// Writes data to the output stream
output.write(array);
// Flushes data to the destination
buffer.flush();
output.close();
} catch (Exception e) {
e.getStackTrace(); }
}
}
Output:
This is a line of text inside the file.


Reader

Reader , is the base class for all Reader subclasses in the Java IO API. A Java Reader is like a Java InputStream except that it is character based rather than byte based. In other words, a Java Reader is intended for reading text (characters), whereas an InputStream is intended for reading raw bytes.

java Reader class

Methods of Reader

Method Description
ready() checks if the reader is ready to be read
read(char[] array) reads the characters from the stream and stores in the specified array
read(char[] array, int start, int length) reads the number of characters equal to length from the stream and stores in the specified array starting from the start
close() Closes the stream and releases any system resources associated with it.

Writer

The Java Writer class (java Writer) is the base class for all Writer subclasses in the Java IO API. A Writer is like an OutputStream except that it is character based rather than byte based. In other words, a Writer is intended for writing text, whereas an OutputStream is intended for writing raw bytes.

java Writer class

Methods of Writer

Method Description
write(char[] array) writes the characters from the specified array to the output stream
write(String data) writes the specified string to the writer
append(char c) inserts the specified character to the current writer
flush() forces to write all the data present in the writer to the corresponding destination
close() closes the writer
InputStreamReader

The InputStreamReader class works with other input streams. It is also known as a bridge between byte streams and character streams. This is because the InputStreamReader reads bytes from the input stream as characters.
import java.io.InputStreamReader;
import java.io.FileInputStream;

class Main {
public static void main(String[] args) {
// Creates an array of character
char[] array = new char[100];
try {
// Creates a FileInputStream
FileInputStream file = new FileInputStream("input.txt");
// Creates an InputStreamReader
InputStreamReader input = new InputStreamReader(file);

// Reads characters from the file
input.read(array);
System.out.println("Data in the stream:");
System.out.println(array);
// Closes the reader
input.close();
}catch(Exception e) {
e.getStackTrace(); }
}
}

Output:
Data in the stream:
This is a line of text inside the file.

OutputStreamWriter

The OutputStreamWriter class works with other output streams. It is also known as a bridge between byte streams and character streams. This is because the OutputStreamWriter converts its characters into bytes.
import java.io.FileOutputStream;
import java.io.OutputStreamWriter;

public class Main {

public static void main(String args[]) {
String data = "This is a line of text inside the file.";
try {
// Creates a FileOutputStream
FileOutputStream file = new FileOutputStream("output.txt");
// Creates an OutputStreamWrite
OutputStreamWriter output = new OutputStreamWriter(file);
// Writes string to the file
output.write(data);
// Closes the writer
output.close();
} catch (Exception e) {
e.getStackTrace(); }
}
}
Output:
This is a line of text inside the file.


FileReader

The Java FileReader class, java. io. FileReader makes it possible to read the contents of a file as a stream of characters. It works much like the FileInputStream except the FileInputStream reads bytes, whereas the FileReader reads characters.
import java.io.FileReader;
class Main {
public static void main(String[] args) {
// Creates an array of character
char[] array = new char[100];
try {
// Creates a reader using the FileReader
FileReader input = new FileReader("input.txt");
// Reads characters
input.read(array);
System.out.println("Data in the file: ");
System.out.println(array);
// Closes the reader
input.close();
} catch(Exception e) {
e.getStackTrace(); }
}
}
Output:
Data in the file:
This is a line of text inside the file.

FileWriter

FileWriter is used to write to character files. Its write() methods allow you to write character(s) or strings to a file. FileWriters are usually wrapped by higher-level Writer objects, such as BufferedWriter or PrintWriter , which provide better performance and higher-level, more flexible methods to write data.
import java.io.FileWriter;

public class Main {
public static void main(String args[]) {
String data = "This is the data in the output file";
try {
// Creates a FileWriter
FileWriter output = new FileWriter("output.txt");
// Writes the string to the file
output.write(data);
// Closes the writer
output.close();
}catch (Exception e) {
e.getStackTrace();}
}
}
Output:
This is a line of text inside the file.


BufferedReader

The BufferedReader maintains an internal buffer of 8192 characters.
During the read operation in BufferedReader, a chunk of characters is read from the disk and stored in the internal buffer. And from the internal buffer characters are read individually.
Hence, the number of communication to the disk is reduced. This is why reading characters is faster using BufferedReader.
import java.io.FileReader;
import java.io.BufferedReader;

class Main {
public static void main(String[] args) {
// Creates an array of character
char[] array = new char[100];
try {
// Creates a FileReader
FileReader file = new FileReader("input.txt");
// Creates a BufferedReader
BufferedReader input = new BufferedReader(file);
// Reads characters
input.read(array);
System.out.println("Data in the file: ");
System.out.println(array);
// Closes the reader
input.close();
}catch(Exception e) {
e.getStackTrace();}
}
}
Output:
Data in the file:
This is a line of text inside the file.

BufferedWriter

The BufferedWriter maintains an internal buffer of 8192 characters.
During the write operation, the characters are written to the internal buffer instead of the disk. Once the buffer is filled or the writer is closed, the whole characters in the buffer are written to the disk.
Hence, the number of communication to the disk is reduced. This is why writing characters is faster using BufferedWriter.
import java.io.FileWriter;
import java.io.BufferedWriter;

public class Main {
public static void main(String args[]) {
String data = "This is the data in the output file";
try {
// Creates a FileWriter
FileWriter file = new FileWriter("output.txt");
// Creates a BufferedWriter
BufferedWriter output = new BufferedWriter(file);
// Writes the string to the file
output.write(data);
// Closes the writer
output.close();
}catch (Exception e) {
e.getStackTrace();}
}
}
Output:
This is a line of text inside the file.