Forgot your password?
typodupeerror
Programming

The Scourge of Error Handling 536

Posted by Soulskill
from the a-user-did-what? dept.
CowboyRobot writes "Dr. Dobb's has an editorial on the problem of using return values and exceptions to handle errors. Quoting: 'But return values, even in the refined form found in Go, have a drawback that we've become so used to we tend to see past it: Code is cluttered with error-checking routines. Exceptions here provide greater readability: Within a single try block, I can see the various steps clearly, and skip over the various exception remedies in the catch statements. The error-handling clutter is in part moved to the end of the code thread. But even in exception-based languages there is still a lot of code that tests returned values to determine whether to carry on or go down some error-handling path. In this regard, I have long felt that language designers have been remarkably unimaginative. How can it be that after 60+ years of language development, errors are handled by only two comparatively verbose and crude options, return values or exceptions? I've long felt we needed a third option.'"
This discussion has been archived. No new comments can be posted.

The Scourge of Error Handling

Comments Filter:
  • On Error Resume next (Score:5, Informative)

    by xaxa (988988) on Saturday December 08, 2012 @12:46PM (#42225661)

    Visual Basic had:
    On Error Resume Next

    I last typed that when I was about 13...

    The documentation [microsoft.com] shows a couple of valid uses for it.

  • by overshoot (39700) on Saturday December 08, 2012 @12:53PM (#42225703)

    How can it be that after 60+ years of language development, errors are handled by only two comparatively verbose and crude options, return values or exceptions?

    Of course, it could be that this just means that your own language horizons are too narrow. Prolog and icon [wikipedia.org] come to mind.

  • Re:The third option (Score:5, Informative)

    by Anonymous Coward on Saturday December 08, 2012 @01:13PM (#42225875)

    Sounds to me like you actually hate abusive exception handling. Exceptions that are in relevant places and handle the errors in meaningful ways are good. I've seen lots of code that actually handles the error, but then I work with competent people (and yes, that is a lovely thing).

    Exception handling can make code cleaner. I'd much rather see a nice exception than return value checking as I can instantly see what kind of error is expected and what should happen if it occurs.

    Please don't dismiss a step forward from return value checking just because you're unfortunate enough to have never worked with anyone who uses it properly.

  • by xaxa (988988) on Saturday December 08, 2012 @02:41PM (#42226543)

    (You probably know all this, but it might be interesting to someone. One of the sysadmins at work could do with reading it...)

    I practically never write scripts for Windows machines, hence never having a genuine use for that VB feature, but on Linux (etc) there's a close-enough equivalent for getting things done; and for shell scripts the default is to continue in case of error. The -e flag to the interpreter prevents this.

    #!/bin/sh
    cd /put/archives/here
    tar cjvf archive-$(date +%Y%m%d).tar.bz2 /files/to/archive/*
    rm -f /files/to/archive/*
    echo "files archived in archive-$(date +%Y%m%d).tar.bz2"

    The cd failing (network down? Disc had errors and wasn't mounted? someone moved the directory?) and the tar failing (filesystem suddenly read-only?) won't stop the rm happening, but "#!/bin/sh -e" would.

    (Alternatively, tar has a --remove-files option, which would prevent removing a file created since tar was executed, but you could still end up with the archive being put in the wrong place.)

    You can let a command fail by using ||, for example:

    #!/bin/sh -e
    cd /put/archives/here
    tar cvf archive-$(date +%Y%m%d).tar /files/to/archive/* --remove-files
    xz --best archive-$(date +%Y%m%d).tar || echo "Compression failed"

  • by JesseMcDonald (536341) on Saturday December 08, 2012 @04:07PM (#42227313) Homepage

    There is at least one other method, which is available natively in Common Lisp. It's known as conditions, and involves registering a condition handler which, unlike an exception handler, runs in the context where the error occurs. The handler has access to zero or more dynamically-scoped restarts, which allow the computation to be resumed at well-defined points without unwinding the entire stack up to where the condition handler was established. The default condition handler is an interactive debugger, which allows the user to examine the state of the program and choose one of the available restarts.

    Beyond Exception Handling: Conditions and Restarts [gigamonkeys.com]

  • by shutdown -p now (807394) on Saturday December 08, 2012 @05:10PM (#42227829) Journal

    This is plainly false. C++ exception is near-zero-overhead, but only for success scenarios - i.e. when no exception is thrown. Actually throwing an exception is quite expensive in most C++ implementations. Java and .NET are similar - no-exception path is very fast, near-zero-overhead, but throwing is expensive.

    Generally, that's exactly the trade-off you make. You can do exceptions cheap if you basically implement them the same as hand-checked error codes, but then you have the overhead of checking for the error code on every single function call - and those do add up. If you don't want that overhead, then you need some form of stack unwinding, where frames that need to inspect thrown exceptions, or to cleanup during unwinding, can register their handlers (and those that don't need either don't do anything at all - it's literally zero overhead for them). But then the exception throwing code has to walk through those handlers and invoke them, which is more costly then just return ERROR_CODE.

The sooner you fall behind, the more time you have to catch up.

Working...