CodeGym /Courses /C# SELF /The finally Block and the throw Operator

The finally Block and the throw Operator

C# SELF
Level 13 , Lesson 2
Available

1. Getting to Know the finally Block

Cleanup and Resource Release

Imagine you're doing experiments in a chemistry lab and, when you're done (or even if you blew up a couple of flasks), you still have to clean up your workspace, wash off the chemicals, and turn off the lights. That's exactly what the finally block is for — it always runs after try and catch, no matter if there was an exception or not.


try
{
    // Here we write "dangerous" code that might throw an exception
}
catch
{
    // Here we catch and handle exceptions
}
finally
{
    // This code will always run, exception or not
}
Structure of try-catch-finally in C#

Why do we need this? Mainly, to make sure resources are always released: close a file, a database connection, unlock the server room door... If there was no finally, after an error some resources could get "stuck" — and that's a real problem. For example, a file could stay locked and not even the admin could open it.

Why not just put everything in catch?

Could we just release the resource in catch? Theoretically, yeah. But if everything goes fine, catch won't run. If you want to be sure the resource is always released, you need finally.

In real life, you often get tasks where it doesn't matter if you succeeded or failed — cleanup is mandatory. That's exactly why finally was invented.

2. Features of the finally Block

When does finally NOT run?

Trick question! finally runs always. Even if there's a return (early exit from the method) in the try block, or a new exception is thrown, finally will still execute.


static void Test()
{
    try
    {
        Console.WriteLine("Before return");
        return;
    }
    finally
    {
        Console.WriteLine("finally will still run!");
    }
}

//Call Test()
Test();
Output:

// Before return
// finally will still run!
    

But if your app suddenly has a "hard crash" (like the computer is turned off, the process is killed, or the whole CLR dies), the finally block won't run. But hey, nothing you can do about that.

The finally Operator and the Call Stack

We'll dig into the call stack more in the next lecture, but for now, just a quick description: it's like a stack of called methods that the program "walks down" if it doesn't find a matching catch.

Another important thing: if an exception happens in try, and it's not caught in catch (like, there's no matching handler), the program leaves the current method and keeps going up the call stack until it finds a matching catch. But before that, the finally block will always run at every stack level.

This guarantees that resources are released properly, even with weird errors.

3. The throw Operator: How to Throw Exceptions Yourself

What is throw and Why Use It

Sometimes just catching an exception isn't enough — sometimes you need to create your own error and "throw" it out. That's exactly what the throw operator is for.


throw new Exception("This is my special error!");
Creating and throwing your own exception

throw literally tells the CLR: "Hey, I just noticed something really bad, I'm throwing my Exception, let whoever called this code deal with it."

throw Without Creating a New Exception

You can use throw; inside a catch block to rethrow the just-caught exception — for example, if you handled part of the error, but want to let higher-level code handle the rest.


try
{
    DangerousOperation();
}
catch (Exception ex)
{
    LogError(ex);
    throw; // rethrows the current exception, call stack info is preserved
}
Rethrowing the current exception while keeping the call stack

If we wrote throw ex;, the call stack info would be lost — that's bad practice.

4. How Does finally Work with throw?

finally Runs Even When Throwing an Exception

Let's check what happens if there's a throw inside try, but we also have a finally:


try
{
    Console.WriteLine("Before the error...");
    throw new Exception("Error during try!");
}
catch
{
    Console.WriteLine("Catch catches the error.");
}
finally
{
    Console.WriteLine("Finally ran.");
}
finally runs even when throwing an exception

Result:


Before the error...
Catch catches the error.
Finally ran.

And if there's no matching catch, finally will still run before the program crashes.

Details: What Happens if You Throw in finally Too?

If a throw happens in finally, that exception will replace the previous one. So info about what happened in try/catch will be lost. That's why it's not recommended to throw in finally if there was already an exception inside.


try
{
    throw new Exception("Error in try");
}
finally
{
    throw new Exception("Error in finally");
}
// Result: "Error in finally" is what gets thrown out
Exception from finally replaces the previous one

5. Practical Tips and Common Mistakes

What Beginners Forget Most Often

  • Not using the finally block for resource cleanup, relying only on catch.
  • Putting code that can throw new exceptions inside finally — this leads to unexpected errors.
  • Forgetting that return inside try doesn't "skip" finally — it always runs.

Alternative to finally: What to Choose?

With the appearance of the using construct (which we'll dig into a bit later), resource cleanup got even easier, but basically, using uses the same finally under the hood. For any non-standard situations (like unlocking or sending an error message) — you still have to use finally.

Why Interviewers Love finally

Every recruiter who's ever written a high-load server loves to ask about finally. They usually ask: "What happens if there's a return in try, and a throw in finally?" or "Is resource cleanup guaranteed when exceptions happen?" And now you don't just have the answers, you actually get it. You can not only explain how finally works, but also why you need it, when to use it, and why no serious code can do without it.

2
Task
C# SELF, level 13, lesson 2
Locked
Simple use of the finally block
Simple use of the finally block
2
Task
C# SELF, level 13, lesson 2
Locked
Rethrowing an Exception
Rethrowing an Exception
Comments
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION