C# Tutorial · Advanced C# · Lesson 18 of 22
C# Exceptions
try, catch, finally, throw, custom exceptions and using.
Handling exceptions
try
{
int[] arr = { 1, 2, 3 };
Console.WriteLine(arr[5]);
}
catch (IndexOutOfRangeException e)
{
Console.WriteLine($"Oops: {e.Message}");
}
finally
{
Console.WriteLine("finally always runs");
}
try { int.Parse("abc"); }
catch (FormatException) when (DateTime.Now.Year > 2000) { Console.WriteLine("Not a number (filtered catch)"); }
Output
Oops: Index was outside the bounds of the array. finally always runs Not a number (filtered catch)
Run this on your computer — see “Get Started” for setup.
Custom exceptions and using
Derive from Exception for domain errors. using disposes resources (files, connections) automatically when they go out of scope:
try
{
using var conn = new FakeConnection("db");
conn.Query("SELECT 1");
throw new InsufficientFundsException(30m);
}
catch (InsufficientFundsException e)
{
Console.WriteLine($"{e.Message} (short by {e.ShortBy})");
}
class InsufficientFundsException(decimal shortBy) : Exception("Insufficient funds")
{
public decimal ShortBy { get; } = shortBy;
}
class FakeConnection : IDisposable
{
private readonly string _name;
public FakeConnection(string name) { _name = name; Console.WriteLine($"open {_name}"); }
public void Query(string sql) => Console.WriteLine($"query: {sql}");
public void Dispose() => Console.WriteLine($"close {_name}");
}
Output
open db query: SELECT 1 close db Insufficient funds (short by 30)
Run this on your computer — see “Get Started” for setup.
Test yourself
What does a using declaration guarantee?
The namespace is importedDispose() is called when the variable goes out of scopeExceptions are ignoredThe object is never null
Show answer
Answer: Dispose() is called when the variable goes out of scope