Introduction
The try/catch
blocks in C# are used to handle exceptions that occur during the execution of a program. Exceptions are runtime errors that disrupt the normal flow of the program. By using try/catch
blocks, you can catch and handle these exceptions gracefully, ensuring that your program continues to run or terminates cleanly.
Basic Structure
Syntax
try
{
// Code that might throw an exception
}
catch (ExceptionType e)
{
// Code to handle the exception
}
Example
using System;
namespace TryCatchExample
{
class Program
{
static void Main(string[] args)
{
try
{
int a = 10;
int b = 0;
int result = a / b;
Console.WriteLine($"Result: {result}");
}
catch (DivideByZeroException ex)
{
Console.WriteLine("Exception caught: Division by zero is not allowed.");
Console.WriteLine($"Exception Message: {ex.Message}");
}
}
}
}
Output
Exception caught: Division by zero is not allowed.
Exception Message: Attempted to divide by zero.
Multiple Catch Blocks
You can use multiple catch
blocks to handle different types of exceptions.
Example
using System;
using System.IO;
namespace MultipleCatchExample
{
class Program
{
static void Main(string[] args)
{
try
{
int[] numbers = { 1, 2, 3 };
Console.WriteLine(numbers[5]); // This will throw IndexOutOfRangeException
string path = "nonexistentfile.txt";
string content = File.ReadAllText(path); // This will throw FileNotFoundException
}
catch (IndexOutOfRangeException ex)
{
Console.WriteLine("Exception caught: Index out of range.");
Console.WriteLine($"Exception Message: {ex.Message}");
}
catch (FileNotFoundException ex)
{
Console.WriteLine("Exception caught: File not found.");
Console.WriteLine($"Exception Message: {ex.Message}");
}
catch (Exception ex)
{
Console.WriteLine("Exception caught: General exception.");
Console.WriteLine($"Exception Message: {ex.Message}");
}
}
}
}
Output
Exception caught: Index out of range.
Exception Message: Index was outside the bounds of the array.
Finally Block
The finally
block is used to execute a set of statements regardless of whether an exception is thrown or not. It is typically used to clean up resources, such as closing file handles or database connections.
Syntax
try
{
// Code that might throw an exception
}
catch (ExceptionType e)
{
// Code to handle the exception
}
finally
{
// Code that runs regardless of an exception
}
Example
using System;
using System.IO;
namespace FinallyBlockExample
{
class Program
{
static void Main(string[] args)
{
StreamReader reader = null;
try
{
reader = new StreamReader("example.txt");
string content = reader.ReadToEnd();
Console.WriteLine(content);
}
catch (FileNotFoundException ex)
{
Console.WriteLine("Exception caught: File not found.");
Console.WriteLine($"Exception Message: {ex.Message}");
}
finally
{
if (reader != null)
{
reader.Close();
Console.WriteLine("File stream closed.");
}
}
}
}
}
Output
Exception caught: File not found.
Exception Message: Could not find file 'example.txt'.
File stream closed.
Throwing Exceptions
You can throw exceptions explicitly using the throw
keyword. This is useful for handling application-specific error conditions.
Syntax
throw new ExceptionType("Error message");
Example
using System;
namespace ThrowExample
{
class Program
{
static void Main(string[] args)
{
try
{
ValidateAge(15);
}
catch (ArgumentOutOfRangeException ex)
{
Console.WriteLine($"Exception caught: {ex.Message}");
}
}
static void ValidateAge(int age)
{
if (age < 18)
{
throw new ArgumentOutOfRangeException("age", "Age must be at least 18.");
}
Console.WriteLine("Age is valid.");
}
}
}
Output
Exception caught: Age must be at least 18. (Parameter 'age')
Custom Exceptions
You can create custom exceptions by deriving from the Exception
class. This is useful for defining application-specific error conditions.
Example
using System;
namespace CustomExceptionExample
{
class Program
{
static void Main(string[] args)
{
try
{
ValidateAge(15);
}
catch (InvalidAgeException ex)
{
Console.WriteLine($"Exception caught: {ex.Message}");
}
}
static void ValidateAge(int age)
{
if (age < 18)
{
throw new InvalidAgeException("Age must be at least 18.");
}
Console.WriteLine("Age is valid.");
}
}
// Custom exception class
public class InvalidAgeException : Exception
{
public InvalidAgeException(string message) : base(message)
{
}
}
}
Output
Exception caught: Age must be at least 18.
Best Practices
- Catch Specific Exceptions: Catch specific exceptions rather than using a general
Exception
catch block. - Log Exceptions: Always log exceptions to help with debugging and monitoring.
- Use Finally for Cleanup: Use the
finally
block to clean up resources like file handles and database connections. - Do Not Swallow Exceptions: Avoid catching exceptions without handling them or logging them.
- Custom Exceptions: Create custom exceptions for application-specific error conditions.
Conclusion
Exception handling in C# using try
, catch
, and finally
blocks is a powerful mechanism to handle runtime errors gracefully. By catching and handling exceptions, you can ensure that your application remains robust and continues to operate smoothly. Proper exception handling is crucial for building reliable and maintainable applications.