C# Exceptions Tutorial For Beginners With Examples

An exception in C# happens when during the execution of a program an error condition occurs.
These exceptions can be generated by the program being executed or by another program being called by the current program. Exceptions can also happen due to the environment in which the application is running or due to any external circumstances.

Exception Handling in C#

When an exception is not handled properly then .NET runtime abruptly halts the execution of a program.
If an exception is handled properly then either the program execution can be continued or can be stopped by doing some meaningful activities like logging the error or performing clean up operations.
Exceptions are handled by using try,catch and finally blocks.
  • try - The code which is suspected to generate an exception should be written inside the try block.
  • catch - The code to handle the exception should be written inside the catch block.
  • finally - The code which must be executed whether an exception is thrown or not should be written inside the finally block.
As a thumb rule, C# exceptions should only be handled when something meaningful can be done with the exception.
Below is an example of a try-catch statement.
    try{
        //code which can generate exception.
    }
    catch(Exception ex)
    {
        //code to handle the exception.
    }
        
Below is an example of a try-catch-finally statement.
    try{
        //code which can generate exception.
    }
    catch(Exception ex)
    {
        //code to handle the exception.
    }
    finally
    {
        //code which must be executed.
    }
        
try-finally statement is also available in C# but it doesn't adds much value as an exception in the try block will halt the execution of the program and the code inside the finally block will not get executed.
C# will not allow a try block without any catch or finally blocks.

Exception types in C#

System.Exception is the base type for all the exceptions in C#. All the other exception classes derive from System.Exception class.
In the below table a hierarchy of standard .NET exception classes are shown.
Exception ClassSummaryBase Class Name
ExceptionAll .NET exceptions derive from this class.Object
SystemExceptionThe exception classes for specific run time errors derive from this class.Exception
IndexOutOfRangeExceptionThrown when there is an error related to the index of an array.SystemException
NullReferenceExceptionWhen an object with a null value is referenced this exception is thrown.SystemException
AccessViolationExceptionThrown when an invalid area of the memory is accessed.SystemException
InvalidOperationExceptionThrown when a program tries to perform an operation on an object which is not valid with respect to the current state of the object.SystemException
ArgumentExceptionAll exceptions related to Argument derive from this exception type.SystemException
ArgumentNullExceptionThis exception is thrown when a null value is passed to a method that do not allow argument to be null.ArgumentException
ArgumentOutOfRangeExceptionIf an argument accepts a range of numeric values and is passed a value that falls out of this range then this exception is thrown.ArgumentException
ExternalExceptionThe exception types for errors that occur outside of .NET common language runtime derive from ExternalException type.SystemException
ComExceptionWhen a COM method called from a .NET class returns an unrecognized HRRESULT then this exception is thrown.ExternalException
SEHExceptionThis exception is thrown when a structured exception handling error is raised by an unmanaged code and when .NET Framework is unable to map this type of error to any other .NET exception type.ExternalException

Explicit Exceptions

Exceptions can be thrown explicitly by using the throw keyword. When a throw keyword is used with in a try block then an exception is thrown explicitly and the control is transferred to the corresponding catch block immediately.
While using the throw keyword inside a try block an exception object has to be passed as argument.
    try{
        Console.WriteLine("Hello World");
        throw(new ApplicationException());
    }
    catch(Exception ex)
    {
        //code to handle the exception.
    }
    
In C#, throw keyword can also be used inside a catch block. This will allow .NET runtime to rethrow the exception. While rethrowing the exception the existing exception object can be manipulated and a new exception can be thrown to the calling program.
As shown in the below example the ApplicationException was changed to FieldAccessExceptioninside the catch block. It is also possible to use a throw keyword inside a catch block without any arguments.
    try
    {
        Console.WriteLine("Hello World");
        throw(new ApplicationException());
    }
    catch (Exception ex)
    {
        //code to handle the exception.
        ex = new FieldAccessException();
        throw (ex);
    }
    

Nesting try-catch blocks

try-catch or try-catch-finally blocks can be nested within another try block or catch block or finally block. When an exception occurs or is thrown in the innermost try block then the control moves to the next catch block matching the exception in the hierarchy.
In the below example the ApplicationException thrown is cascaded to the outermost catch block where the exception message is shown to the user.
        
    ArrayList list = new ArrayList();
    try
    {
        try
        {
            list.Add(1234);
            list.Add("hello");
            
            if (list.Count < 2)                    
                throw (new ApplicationException());
        }
        catch (ApplicationException ex)
        {
            throw(ex);
        }
        finally
        {
            Console.WriteLine("finally");
        }
    }
    catch (Exception ex)
    {           
        //The exception thrown from the inner try block will be caught here.
        Console.WriteLine(ex.Message);
    }
        

Properties of Exception Class

Since Exception class is the base class from which all other exception types derive hence the properties available in the base Exception class is also available to all other derived exception types.
The properties available are:
  • Data - This is a Dictionary object that provides information about the exception. A for loop can be used to read it's keys and values.
  • HelpLink - Is used to provide a link to a help file. This property is mostly used in a custom exception class.
  • InnerException - When one exception triggers another exception then this property is used to preserve the original exception message.
  • Message - Stores the message related to a exception.
  • Source - This property returns the assembly where the exception was raised. This property can also be set with a custom value in a program.
  • StackTrace - This property is used to determine the place where the actual exception occurred. It provides a stack trace with program line number and source file name where the exception was generated.
  • TargetSite - This is a readonly property which stores the method name from which the exception originated.