0

I was wondering if there is a right place to handle exceptions. Should I handle it inside my method or should I handle it at the method call? Or does it matter at all?

I'm sorry, but I couldn't find anything about this (googling "exception handling scope" didn't returned what I was looking for).

Example:

// this way...
void readFile(string file)
{
    try
    {
        /* do my stuff */
    }
    catch(Exception exception)
    {
        /* handle exception */
    }
}

int main()
{
    readFile(file);
}

// or this way?
void readFile(string file)
{
    /* do my stuff */
}

int main()
{
    try
    {
        readFile(file);
    }
    catch(Exception exception)
    {
        /* handle exception */
    }
}

Thanks in advance.

efermat
  • 45
  • 4
  • 1
    People please stop answering this massive duplicate. – John Saunders Nov 16 '11 at 18:16
  • 1
    I'm sorry, but, as I said, I couldn't find anything that answered my question. I would appreciate if you could post links to duplicates or even tell me some 'search terms'. – efermat Nov 16 '11 at 18:29
  • @John: if it's a duplicate, vote to close. – Igby Largeman Nov 16 '11 at 18:45
  • @Charles: good suggestion. I will if I have time to find the dupe and it not closed yet. – John Saunders Nov 16 '11 at 18:50
  • @John perhaps this one: http://stackoverflow.com/questions/1050282/general-exception-handling-strategy-for-net (look who's answer is accepted!) – Igby Largeman Nov 16 '11 at 18:57
  • Thanks for finding that. I have now favorited it so I can find it next time. It's come up at least three times this week. Don't know who that Saunders guy is though, don't listen to anything he says. – John Saunders Nov 16 '11 at 18:59

5 Answers5

4

In general you want to handle the error where it makes sense to do so.

If in your example above you want to try to read a file and if that fails then read a default file the you can handle it as in the first example.

If the readFile operation failing is vital to the rest of main() then you need to have the exception passed up to that so it can deal with whatever fallout is for readFile() failing and this would be as in your second example.

Of course you can always handle the error (or some possible exceptions) inside the method and rethrow or let some pass through or whatever.

Really though its your program flow that determines where your exception handling goes. Handle the exception where it makes sense to do so.

Chris
  • 27,210
  • 6
  • 71
  • 92
3

The first approach is usually better, since all the file stuff is handled by readFile and code calling readFile does not have to worry about file handling issues. You could however return a boolean from readFile telling the caller if the operation succeded:

bool readFile(string file)
{
    try {
        /* do my stuff */
        return true;
    } catch(Exception exception) {
        /* handle exception */
        return false;
    }
}
Olivier Jacot-Descombes
  • 104,806
  • 13
  • 138
  • 188
  • What if the caller of readFile wants to do something else with the exception than what you are doing? The upper code won't have any access to the Exception details. – Tudor Nov 16 '11 at 18:21
  • How about passing an Exception as a "ref" or "out" parameter? Note that if one wants caller to recover without having to use Pokemon exception exception handling, letting exceptions bubble up the call stack is not a reasonable option. One must either wrap and rethrow the exception, or one must via some other means let the caller know that the operation failed in a fashion which didn't corrupt the rest of the system. If the caller's going to be anticipating the exception, returning it as a "ref" or "out" parameter seems better than wrapping and rethrowing it. – supercat Nov 16 '11 at 18:29
  • You are both right, different approaches are possible. It always depends what you want to do. Nevertheless, personally if find it easier to deal with methods which do not throw exceptions and confine problems instead of propagating them. – Olivier Jacot-Descombes Nov 16 '11 at 18:50
1

If you can handle the exception, recover from it and continue, then you should do that immediately.

On the other hannd, if there is nothing sensible you can do to handle the exception then the best thing is to let the exception propagate up the call stack. Eventually code at the top-level will be forced to catch the exception and log it / show it to the user, or else the application will crash.

Mark Byers
  • 811,555
  • 193
  • 1,581
  • 1,452
1

Only handle the exception if you actually plan on doing something unique in that particular circumstance (e.g. talking to a DB and a deadlock exception occurs you may wish to retry the DB operation). If you just want to do some generic exception handling action (e.g. log every exception) do it in the highest level possible (usually the UI) and don't clutter your code up with exception handlers everywhere - just let the exceptions bubble up.

Dylan Smith
  • 22,069
  • 2
  • 47
  • 62
0

The best practice is to let the upper levels handle the exception. Imagine that you are packing your low level file reader in a library and handling the exception there. You are not giving the users of your code the ability to handle the exception in the way that they desire.

Tudor
  • 61,523
  • 12
  • 102
  • 142
  • I know Eric Lippert likes the idea of letting exceptions ripple up to the top level as-is, but I disagree. Suppose an implementation of IDictionary.Add calls a method which throws an InvalidOperationException. A caller may be expecting to catch InvalidOperationException, and think that such an exception would mean the dictionary already held the key but was otherwise in a legitimate state. Catching, wrapping, and rethrowing exceptions would seem like the best way to avoid that problem. Too bad the existing exception mechanisms don't make that particularly convenient. – supercat Nov 17 '11 at 16:40