Working with the File Type

Like FileInfo, File supplies AppendText(), Create(), CreateText(), Open(), OpenRead(), OpenWrrite(), and OpenText() methods.

var fileName = $@"C{Path.VolumeSeparatorChar}{Path.DirectorySeparatorChar}temp{Path.DirectorySeparatorChar}Test.dat";
using(FileStream fs8 = File.Create(fileName))
 {
     // Use the fileStream object
 }
File.Delete(fileName);
// Make a new File via FileInfo.Open()
using(FileStream fs9 = File.Open(fileName, FileMode.OpenOrCreate, FileAccess.ReadWrite, FileShare.None))
 {
     // Use the filestream object...
 }
// Get a FileStream object with read-only permissions.
using(FileStream readOnlyStream = File.OpenRead(fileName))
{
}
File.Delete(fileName);
// Get a FileStream object with-write-only permissions.
using(FileStream writeOnlyStream = File.OpenWrite(fileName)) { }
// Get a StreamReader object.
using(StreamReader sReader = File.OpenText(fileName)) { }
File.Delete(fileName);
// Get some StreamWriter
using(StreamWriter sWriter = File.CreateText(fileName)) { }
File.Delete(fileName);
using(StreamWriter sWriterAppend = File.AppendText(fileName)) { }
File.Delete(fileName);

Additional File-Centric Members

  1. ReadAllBytes() : Opens the specified file, returns the binary data as an array of bytes, and then closes

the file

  1. ReadAllLines() : Opens a specified file, returns the character data as an array of strings, and then

closes the file

  1. ReadAllText() : Opens a specified file, returns the character data as a System.String, and then closes

the file

  1. WriteAllBytes() : Opens the specified file, writes out the byte array, and then closes the file
  2. WriteAllLines() : Opens a specified file, writes out an array of strings, and then closes the file
  3. WriteAllText() : Opens a specified file, writes the character data from a specified string, and then

closes the file

The Abstract Stream Class

In the work of I/O manipulation, a stream represents a chunk of data flowing between a source and a destination. Streams provide a common way to interact with a sequence of bytes, regardless of what kind of device stores or displays the bytes in question.

System.IO.Stream (Abstract Stream Members)

  1. CanRead
  2. CanWrite
  3. CanSeek

Determines whether the current stream supports reading, seeking, and/or writing.

  1. Close() : Closes the current stream and releases any resources (such as sockets and file handles)

associated with the current stream. Internally, this method is aliased to the Dispose()

method; therefore, closing a stream is functionally equivalent to disposing a stream.

  1. Flush() : Updates the underlying data source or repository with the current state of the buffer and

then clears the buffer. If a stream does not implement a buffer, this method does nothing.

  1. Length : Returns the length of the stream in bytes.
  2. Position : Determines the position in the current stream.

  1. Read()
  2. ReadByte()
  3. ReadAsync()

Reads a sequence of bytes (or a single byte) from the current stream and advances the

current position in the stream by the number of bytes read.

  1. Seek() : Sets the position in the current stream.
  2. SetLength() : Sets the length of the current stream.
  3. Write()
  4. WriteByte()
  5. WriteAsync()

Writes a sequence of bytes (or a single byte) to the current stream and advances the

current position in this stream by the number of bytes written.

Working with FileStreams

The FileStream class provides an implementation for the abstract Stream members in a manner appropriate for file-based programming. It's a primitive stream. It can read or write only a single byte or an array of bytes.

using (FileStream fStream = File.Open("myMessage.dat",FileMode.Create))
 {
     // Encode a string as an array of bytes.
     string msg = "Hello!";
     byte[] msgAsByteArray = Encoding.Default.GetBytes(msg);
     // Write byte[] to file.
     fStream.Write(msgAsByteArray, 0, msgAsByteArray.Length);
     // Reset internal position of stream.
     fStream.Position = 0;
     // Read the types from file and display to console.
     Console.Write("Your message as an array of bytes: ");
     byte[] bytesFromFile = new byte[msgAsByteArray.Length];
     for (int i = 0; i < msgAsByteArray.Length; i++)
     {
         bytesFromFile[i] = (byte)fStream.ReadByte();
         Console.Write(bytesFromFile[i]);
     }
     // Display decoded messages.
     Console.Write("\nDecoded Message: ");
     Console.WriteLine(Encoding.Default.GetString(bytesFromFile));
     Console.ReadLine();
 }
File.Delete("myMessage.dat");

Working with StreamWriter and StreamReaders

The StreamWriter and StreamReader classes are useful whenever you need to read or write character-based data (e.g. strings). Both work by default with Unicode characters; however, you can change this by supplying a properly configured System.Text.Encoding object reference.

StreamReader derives from an abstract type named TextReader which provides the ability to read and peek into a character stream.

StreamWriter derives from an abstract class named TextWriter. This class defines members that allow derived types to write textual data to a given character stream.

Core Members of TextWriter

  1. Close() : This method closes the writer and frees any associated resources. In the process, the buffer is automatically flushed (Close() = Dispose()).
  2. Flush() : This method clears all buffers for the current writer and causes any buffered data to be written to the underlying device; however, it does not close the writer.
  3. NewLine : This property indicates the newline constant for the derived writer class (windows=\r\n)
  4. Write() and WriteAsync() : This overloaded method write data to the next stream without a newline constant.
  5. WriteLine() and WriteLineAsync() : This overloaded method write data to the next stream with a newline constant.

Writing To a Text File

using(StreamWriter writer = File.CreateText("reminders.txt"))
 {
     writer.WriteLine("Don't forget 1");
     writer.WriteLine("Don't forget 2");
     writer.WriteLine(writer.NewLine);
 }

Reading from a Text File

TextReader Core Members

  1. Peek() : Returns the next available character without changing the position of the reader. A value of -1 indicates you are at the end of the stream.
  2. Read() and ReadAsync() : Reads data from an input stream.
  3. ReadBlock() and ReadBlockAsync() : Reads a specified maximum number of characters from the current stream and writes the data to a buffer, beginning at a specified index.
  4. ReadLine() and ReadLineAsync() : Reads a line of characters from the current stream and returns the data as a string (a null string indicate EOF).
  5. ReadToEnd() and ReadToEndAsync() : Reads all characters from the current position to the end of the stream and returns them as a single string.

using(StreamReader sr = File.OpenText("reminders.txt"))
 {
     string input = null;
     while((input = sr.ReadLine()) != null)
     {
         Console.WriteLine(input);
     }
 }
 

Directly Creating StreamWriter/StreamReader Types

// Get a StreamWriter and writes string data.
using(StreamWriter writer = new StreamWriter("reminders.txt")) { }
// Now read data from file.
using(StreamReader reader = new StreamReader("reminders.txt")) { }

Working with StringWriters and StringReaders

You can use the StringWriter and StringReader types to treat textual information as a stream of in-memory characters.

// Create a StringWriter and emit character data to memory.
using(StringWriter strWriter = new StringWriter())
 {
     strWriter.WriteLine("Don't forget 1");
     Console.WriteLine(strWriter);
 }

StringWriter and StreamWriter both derive from the same base class (TextWriter), so the writing logic is similar.

StringBuilder sb = strWriter.GetStringBuilder();
sb.Insert(0, "Hey!");
Console.WriteLine(sb.ToString());
sb.Remove(0, "Hey!".Length);

Working with BinaryWriters and BinaryReaders

The final writer/reader sets you will examine in this section are BinaryReader/BinaryWriter. Both derive directly from System.Object.

BinaryWriter Core Members

  1. BaseStream : This read-only property provides access to the underlying stream used with the BinaryWriter

object.

  1. Close() : This method closes the binary stream.
  2. Flush() : This method flushes the binary stream.
  3. Seek() : This method sets the position in the current stream.
  4. Write() : This method writes a value to the current stream.

BinaryReader Core Members

  1. BaseStream : This read-only property provides access to the underlying stream used with the BinaryReader

object.

  1. Close() : This method closes the binary reader.
  2. PeekChar() : This method returns the next available character without advancing the position in the

stream.

  1. Read() : This method reads a given set of bytes or characters and stores them in the incoming array.
  2. ReadXXXX() : The BinaryReader class defines numerous read methods that grab the next type from the

stream (e.g., ReadBoolean(), ReadByte(), and ReadInt32()).

// Open a binary writer for a file.
FileInfo f = new FileInfo("BinFile.dat");
using (BinaryWriter bw = new BinaryWriter(f.OpenWrite()))
{
     // Print out the type of BaseStream.
     // (System.IO.FileStream in this case).
     Console.WriteLine("Base stream is: {0}", bw.BaseStream);
     // Create some data to save in the file.
     double aDouble = 1234.67;
     int anInt = 34567;
     string aString = "A, B, C";
     // Write the data.
     bw.Write(aDouble);
     bw.Write(anInt);
     bw.Write(aString);
}