I don't understand the difference between these two classes. When would you use one over the one? I know that FileWriter can output characters to a file but so can OutputStreamWriter as far as i know. Here is some code that i tested and they seem to work the same, i'm not adding the exception handling stuff but lets just assume its there.
FileWriter writer = new FileWriter("C:\\Users\\owner\\Desktop\\demo.txt"); writer.write("hello"); writer.close();
I also tried this code:
File file = new File("C:\\Users\\owner\\Desktop\\demo.txt"); os = new OutputStreamWriter(new FileOutputStream(file)); os.write("hello"); os.close();
Both of these seem to work the same for me. The only time something strange happens is when i try to put an int value in the write() method. For the FileWriter example, my demo.txt is completely empty. For the OutputStreamWriter example i get some weird symbols in my text file. I am reading a java book and the only explanation i get for OutputStreamWriter is that it "converts a stream of characters to a stream of bytes" so shouldn't i be seeing some bytes in my text file in the second example?
Some clarification would be greatly appreciated.
FileWriter writes streams of characters while FileOutputStream is meant for writing streams of raw bytes. FileWriter deals with the character of 16 bits while on the other hand, FileOutputStream deals with 8-bit bytes.
FileWriter writes directly into Files and should be used only when the number of writes is less. BufferedWriter: BufferedWriter is almost similar to FileWriter but it uses internal buffer to write data into File. So if the number of write operations is more, the actual IO operations are less and performance is better.
If you have a lot of code that appends a single character at a time, however, a BufferedWriter will be much more efficient. As per andrew's comment below, the FileWriter actually uses its own fixed-size 1024 byte buffer. This was confirmed by looking at the source code.
It is not necessary to close it, because BufferedWriter takes care of closing the writer it wraps.
XXXInputStream and XXXOutputStream (where XXX varies, there's a lot of options) deal with 8-bit bytes. For example, OutputStream.write(byte[] c);
XXXWriter or XXXReader deal with 16-bit chars. For example, Reader.read(char[] cbuf)
.
OutputStreamWriter converts an OutputStream to a Writer. As you may have guessed, InputStreamReader converts from an InputStream to a Reader. I am unaware of any classes that do the reverse, i.e. convert a Reader to an InputStream.
FileWriter is a Writer that talks to files. Since a Java String internally uses chars (16 bit so they can handle Unicode), FileWriter is the natural class for use with Unicode Strings.
FileOutputStream is an OutputStream for writing bytes to a file. OutputStreams do not accept chars (or Strings). By wrapping it in an OutputStreamWriter you now have a Writer, which does accept Strings.
Now, the real question, is when do you use a Reader/Writer and when a Stream? I've used Java for years and sometimes I get confused too. I believe the following to be correct:
Handy Guide - How to Decide Which to use:
Some other links:
inputstream and reader in Java IO
InputStream vs InputStreamReader
There is actually no difference per se, FileWriter
is just a convenience class. It extends OutputStreamWriter
and creates the needed FileOutputStream
itself.
Regarding write(int)
: that method writes a single character with the specified codepoint to the stream, it does not write a textual representation of the numeric value.
As for the empty file, note that you should always flush the buffer when you want the things you've written flushed to the underlying store (be it a file or a network stream or whatever you can think of). Simply call os.flush()
after writing, that should do it.
EDIT: As Thilo has correctly mentioned, closing the stream should already flush it (and all underlying streams).
And last but not least, you should nearly always explicitly specify the charset/encoding you want your Writer to write in. Writers write characters, while OutputStreams write bytes, so you have to specify how those characters should be encoded into bytes. If you don't specify an encoding, the system default gets used, which may not be what you want.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With