1. Introduction
StreamWriter is one of the key classes in the System.IO namespace in .NET, designed to make writing text data to files via streams super convenient.
Why not just use FileStream directly?
FileStream only deals with bytes. If you try to write a string with it, you'll have to convert the text to bytes yourself and handle the encoding (trust me, you'll want to come back to StreamWriter after that).
StreamWriter takes care of all that hassle for you: you give it a string—it writes the right bytes to the file.
Main advantages:
- It's easy to write strings without thinking about converting to bytes.
- There are methods for writing text line by line.
- You can control buffering and encoding (and we'll learn how to use that too).
Basic Example
using System.IO;
string path = "output.txt";
using (StreamWriter writer = new StreamWriter(path))
{
writer.WriteLine("Hello, world!");
writer.WriteLine("This is the second line.");
}
// After leaving the using curly braces, StreamWriter will definitely release the file.
What's happening here?
- The file is opened for writing (if it doesn't exist—it'll be created).
- Each string is written as a separate line in the file (the WriteLine method).
- After the using block, the file is automatically closed, even if errors happen.
If you open the output.txt file after running this program, you'll see two lines of text, just as expected.
Important Note
If the file already exists, it will be overwritten from scratch! Everything that was inside—gone. So be careful: don't keep your important thesis or the only copy of your utility bill in such files.
2. Writing Data to a Stream
Main StreamWriter Methods
| Method | Description |
|---|---|
|
Writes a string without a line break |
|
Writes a string with a line break |
|
Forces the buffer to be written to the file (rarely needed manually) |
/ |
Closes the stream and releases the resource (what using does) |
|
Access the underlying stream (for example, FileStream) |
The Write() Method
Writes data without moving to a new line. Everything you write next will end up on the same line in the file.
The WriteLine() Method
Writes data and automatically adds an end-of-line character (\r\n on Windows, \n on Unix-like OSes).
It's like hitting Enter after every write.
Write() vs WriteLine(): showing the difference
using (var writer = new StreamWriter("example.txt"))
{
writer.Write("First ");
writer.Write("paragraph. ");
writer.WriteLine("Finished the line, Enter!");
writer.Write("Second paragraph.");
}
Now example.txt will look something like this:
First paragraph. Finished the line, Enter!
Second paragraph.
3. Working with Encodings
By default, when you create a StreamWriter without specifying parameters, it uses UTF-8 encoding with BOM (Byte Order Mark).
In practice, that's convenient and modern, but sometimes you need to set the encoding explicitly—for example, for compatibility with old programs or imported data.
How to specify encoding?
// Write a file in Windows-1251 encoding (Cyrillic for old systems)
using (var writer = new StreamWriter("cyrillic.txt", false, System.Text.Encoding.GetEncoding("windows-1251")))
{
writer.WriteLine("Hello, Cyrillic world!");
}
Important point:
The encoding must be supported on your system. If you're not sure—stick with UTF-8.
4. Extra Constructor Parameters
Let's peek under the hood of StreamWriter:
public StreamWriter(
string path, // path to the file
bool append = false, // append to the end of the file?
Encoding encoding = null, // encoding
int bufferSize = 1024 // buffer size, bytes
)
- append—if false (default), the file will be overwritten. If true, new entries are added to the end.
- encoding—the encoding used.
- bufferSize—the size of the internal buffer for speeding up work with large amounts of data.
Example: appending to the same file
// The file will be appended to, not overwritten
using (var writer = new StreamWriter("log.txt", append: true))
{
writer.WriteLine(DateTime.Now + " -- New event");
}
5. Useful Tips
What happens with appending and overwriting
| Mode | What does it do? | Result in file |
|---|---|---|
| append: false | Overwrites everything from scratch | Old data is erased |
| append: true | Adds new lines to the end | Old lines are kept |
Tip: Append mode (append: true) is a great choice for logging when you want to keep a history of events.
StreamWriter and large amounts of data
- StreamWriter buffers writes: the actual data will hit the file a bit later than when you called WriteLine. But after closing the stream (or calling Flush()), everything is guaranteed to be on disk.
- Writing with WriteLine is super efficient for line-by-line output. For complex formats (JSON, CSV, or XML) it's better to use the right libraries, or carefully escape special characters (like commas or quotes).
How to properly finish writing and release resources
The right way: always use using!
That way you guarantee the file will be closed, even if an exception happens (like if the disk suddenly "runs out" or another program locks the file).
6. Practical Examples
Let's say in this course we have a mini book-tracking program. Let's add the ability to write new books to a file.
Example: Saving a new book to a separate file
using System;
using System.IO;
class Program
{
static void Main()
{
Console.WriteLine("Enter the book title:");
string bookTitle = Console.ReadLine();
Console.WriteLine("Enter the author:");
string author = Console.ReadLine();
string path = "books.txt";
using (var writer = new StreamWriter(path, append: true))
{
writer.WriteLine($"{bookTitle};{author}");
// CSV format: each line is a separate book, separated by semicolon
}
Console.WriteLine("Book saved to file!");
}
}
Try adding a few books in a row. In the books.txt file, lines will be added without erasing the previous ones. This behavior is handy for keeping logs or journals—for example, for your future audit system when you grow up to be an Enterprise developer.
7. How to avoid common mistakes when writing to a file
Most newbies run into these issues:
File not closed and locked by another process. Reason—you forgot about using.
Wrote a bunch of lines, but the file is empty: forgot to call Flush() or close the stream (but with using this happens automatically).
Accidentally overwrote the file instead of appending—forgot to set append: true.
Encoding problems: file opens as "gibberish" in Notepad—wrong encoding chosen or another program doesn't support UTF-8.
Exceptions UnauthorizedAccessException or DirectoryNotFoundException: the program tries to save the file somewhere it doesn't have permission, or in a folder that doesn't exist. Check the path and access rights.
Error "file is used by another process": you opened the file for writing but didn't close it, or someone else is trying to write to it at the same time.
GO TO FULL VERSION