Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Are try/catch for every single statement that throws an exception considered an anti-pattern?

I am currently reviewing a colleagues Java code, and I see a lot of cases where every single statement that may throw an exception being encapsulated in its own try/catch. Where the catch block all perform the same operation (which operation is not relevant for my question).

To me this seems like a code smell, and I do remember reading about it being a common anti-pattern. However I cannot find any references on this.

So are try/catch for every single statement that throws and exception considered an anti-pattern, and what are the argument supporting this?


Constructed example: (Does not relate to the original problem, so please don't mind other problems with this example, as it is just constructed to illustrate what I mean.)

public int foo()
{
    int x, y = 7;

    try
    {
        x = bar(y);
    }
    catch(SomeException e)
    {
        return 0;
    }

    try
    {
        y = baz(x,y);
    }
    catch(SomeOtherException e)
    {
        return 0;
    }

    /* etc. */

    return y;
}

(Assume that it is appropriate to catch both exceptions here, i.e. we know what do with them, and the appropriate thing is to return 0 in both cases.)

like image 361
Bjarke Freund-Hansen Avatar asked Aug 17 '11 12:08

Bjarke Freund-Hansen


2 Answers

I can't serve you with an authoritative source, but these are fundamental tenets of exception handling:

  • exceptions should be caught at the point where one can properly handle them, and
  • you must not swallow exceptions - there should always be (at least) a trace of an exception thrown, so the minimum is to log it, so that at least the developers get a chance of noticing that something bad happened. Which leads to the third point:
  • exceptions should only be used to signal exceptional bad events, not to control program flow.

There are lots of earlier posts on SO dealing with this, for example Best practices for exception management in JAVA or C#.

like image 114
Péter Török Avatar answered Nov 09 '22 05:11

Péter Török


My initial reaction was that this is a bad thing. (Also I initially had arguments about catching exceptions in general, but removed those to focus on the example given in the question.) Returning 0 on an exception is hard to judge here because it's unknown what bar and baz do, and what the exceptions represent. If the caller really doesn't need to know anything went wrong, and the caller doesn't have to distinguish between the return value as error condition and return value as data, then this is ok. On the other hand if the exceptions thrown are problems with resources not being available it is better to fail fast than try to struggle on.

I am doubtful this is a good thing because if it is reasonable for this code to return 0 on an exception, it would have been at least as reasonable for bar and baz to return 0 in the first place.

To address catching exception for every single statement in general (as opposed to returning immediately with a default value as the example does), that is a bad thing because once you have an exception thrown, something has gone wrong and your method or object can be in a bad state. The purpose of exception-handling is to have a means of escaping a context where something has gone wrong and getting back to a place with a known state. If catching every single exception and blundering on was ok, all our languages would support `On Error Resume Next'.

like image 21
Nathan Hughes Avatar answered Nov 09 '22 04:11

Nathan Hughes