Search code examples
pythonexceptionzen-of-python

What is preferable way to handle exceptions?


If I'm not sure at something while writing some code I'm trying to read The Zen of Python once more. For this time those lines hesitate me.

Errors should never pass silently.
Unless explicitly silenced.

At current code I have some functions which might look like this:

def add_v_1(a, b):
    return a + b 

And all calls for them like:

c = add_v_1(7, [])

Exception for such code will bubble up and caught at upper layers.

But should it be like this?

add_v_1 can raise TypeError exception and I want to recover from it. So, the possible call of function would be:

try:
    c = add_v_1(7, [])
except TypeError:
    print "Incorrect types!"

But for every call, I should do that exception handling. Which looks to heavy.

So, I can do:

def add_v_2(a, b):
    try:
        return a + b
    except TypeError:
        print "Incorrect types!"

and a call would be:

c = add_v_2(7, [])

which looks cleaner.

Seems all of those approaches follow The Zen of Python but which one of them is better choice?


Solution

  • With reference to your example, it's debatable as to whether you should catch the exception inside the function. Doing so will return None from the function, which then burdens the calling code with checking the return value of the function, and treating None as an error. It effectively replaces exception handling with error checking. The former is generally more Pythonic.

    You should ask whether it makes sense to catch an error such as attempting to add 2 completely different data types. Doing so in this case would seem to be a programming error, not really the sort of thing that you would expect during normal execution.

    And what could you do to handle such an error? There doesn't seem to be any useful value that could be returned within the domain of the function's expected output... other than None to signal that a result could not be produced. But the calling code still has to perform some kind of error checking... so it might as well just handle an exception - at least it only has to handle that once.

    But the example is contrived, and it's difficult to give blanket advice. In this particular situation, for the reasons above, I would allow the exception to propagate to the calling code and handle it there.