Live data from Hacker News

You’re better off using Exceptions

eiriktsarpalis.wordpress.com

191–200 of 242 posts

Re: You’re better off using Exceptions

#191

Earlier quoted context omitted.

In C++, exceptions are often faster than manual error checking when errors are rare. But C++ does not provide a stack trace.

You don’t always get a stack trace, but it still has to unwind the stack, calling destructors as needed, and check the exception’s type against each catch block.

Hence 'when errors are rare'.

Re: You’re better off using Exceptions

#192

Earlier quoted context omitted.

You don’t always get a stack trace, but it still has to unwind the stack, calling destructors as needed, and check the exception’s type against each catch block.

Hence 'when errors are rare'.

I guess we’re violently agreeing? Exceptions are an order of magnitude (or several orders) slower than function calls and returns; but that can still be efficient overall, if only a tiny fraction of calls fail.

I’d simply add that most people greatly underestimate how expensive exceptions are, even in C++.

Re: You’re better off using Exceptions

#193

Earlier quoted context omitted.

>> A record not being found is a normal thing! > It's not a normal thing for code that needs that record that wasn't found. This is something of a religious dispute and there are arguments both ways. But I think it’s important to note that an exception is vastly more expensive than a simple function call or return value. So I’d say you need a really good reason to use exceptions. I agree with the GP that in general,…

I don't see what the problem is. The API should expose two methods: `fetch()` which returns, say, nil if there's no result (or an error monad or error tuple, depending on your language), and say `fetch!()` (or `fetch_throws()` if your language doesn't support exclamation points) which raises an exception if there isn't a result. The programmer gets to choose, on a case-by-case basis.

Agreed, it’s ideal to have both options available.

Kotlin gets this right for the most part (although I think it would be better if it had checked exceptions).

Re: You’re better off using Exceptions

#194

The real problems with exceptions are that they have a large performance overhead, and that they differentiate poorly between anticipated errors and truly exceptional situations. The performance overhead comes from grabbing a stack trace and constructing an object that lives on the heap, and then unwinding the stack. (Some assembly experts can probably explain this overhead better than I can.). When your code handles…

Exceptions don't generally have a large performance overhead, they do in C++. Ocaml exception handling for example was orders of magnitude faster last I looked. And C++ itself is seeking to fix the super-slow design: http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2018/p070....

Re: You’re better off using Exceptions

#195

Good article but it is tangential to a basic design issue. Error handling should be done at the edges of systems rather than in the center. If you do that, it doesn't matter whether you use exceptions or error monads, you have a pure core that doesn't need to deal with error handling and a very slim area to catch errors. The mechanism you use for error handling, at that point, doesn't matter. The problems of error ha…

it's not trivial in every domain to distinguish between pure and non-pure operations. If you're writing software for control systems, robotics, anything that has a very tight, low-level coupling between programming logic and the outside world it's harder or often not possible to separate concerns into some sort of data -> logic pipeline that lends itself to this style of programming, or it may come at the cost of performance.

Re: You’re better off using Exceptions

#196
post #62

Earlier quoted context omitted.

> A record not being found is a normal thing! It's not a normal thing for code that needs that record that wasn't found. > They literally tell you nothing and there's no way to solve them without catching/rescuing them. A null value, a plain "error" object, or an error argument in a callback would have been sufficient. If I need an exception to be raised for this kind of thing, I'll do it myself. They tell you lots:…

> It's not a normal thing for code that needs that record that wasn't found. No offense, but I don't know where that idea comes from. Systems are checking for records all the time in ways where the absence of data doesn't necessitate throwing an exception. For instance, a page, user, or piece of media on a website may have existed at one point but was since deleted, but still has a permalink floating around the net.…

Your first example loses the real reason for the error and just assumes "record-not-found", so it will give misleading errors when the network drops for a moment, possibly resulting in an attempt to insert a duplicate record if the code tries to add-if-not-found. That'll make for some debugging fun!

And this is the problem with error checks: They're purely optional as far as the language is concerned, so we keep getting them wrong or forgetting things, even when we're being careful.

Re: You’re better off using Exceptions

#197
post #62

Earlier quoted context omitted.

> A record not being found is a normal thing! It's not a normal thing for code that needs that record that wasn't found. > They literally tell you nothing and there's no way to solve them without catching/rescuing them. A null value, a plain "error" object, or an error argument in a callback would have been sufficient. If I need an exception to be raised for this kind of thing, I'll do it myself. They tell you lots:…

> It's not a normal thing for code that needs that record that wasn't found. No offense, but I don't know where that idea comes from. Systems are checking for records all the time in ways where the absence of data doesn't necessitate throwing an exception. For instance, a page, user, or piece of media on a website may have existed at one point but was since deleted, but still has a permalink floating around the net.…

@Seenso You probably won't find, this, but I think I somewhat misunderstood the first thing you said.

My response to that would be that if it isn't a normal thing for your code to encounter a record not being found, then you should handle that state in whatever you see fit, whether that's by passing down a value or object reflecting that error state or throwing your own exception(yes, I do think such a thing can be appropriate). I still don't favor the latter, but at least with throwing your own exception your application can catch it at a higher level and will be less likely to mistake it for another exception of the same class that should be handled differently. If you are using an SDK that throws an error for a "record not found" type situation, it would certainly work in your favor if your application really does benefit from it, but I think a lot of code doesn't actually call for such a thing.

But my point is that there's no reason I can think of that an exception can't be totally optional in these circumstances. I don't think it should be assumed that everyone wants an exception. There's a reason why we use conditional syntax like if-statements because, if used try-catch syntax as control flow for everything, the flow would be bass ackwards and hard to understand. In my opinion, the example situation I described is on the borderlands where an exception might make sense but probably doesn't actually make things better.

Every project is different, and people might choose to use exceptions a lot, which is fine for them. I've personally been better off not relying on the exception-based control flow taught to me when I learned Ruby, but that doesn't mean I would come into a project and remove everyone's exception handling.

Re: You’re better off using Exceptions

#198
post #134

Earlier quoted context omitted.

> It's not a normal thing for code that needs that record that wasn't found. No offense, but I don't know where that idea comes from. Systems are checking for records all the time in ways where the absence of data doesn't necessitate throwing an exception. For instance, a page, user, or piece of media on a website may have existed at one point but was since deleted, but still has a permalink floating around the net.…

The code example is not convincing at all. Obviously a single if is much cleaner than a single try/catch block but that is not the comparison. The if needs to be replicated N times for every N things that could fail and that are calling each other in a potentially deep call hierarchy. The try/catch block only needs to occur once at a level that is above all of the N things that might fail.

That doesn't always make sense when you're dealing with a generic exception class. What you are assuming is that a try-catch block higher up in the hierarchy can handle a RecordNotFound exception for all its descendants, but that's not necessarily going to be the case. It's basically the inheritance problem in object-oriented programming, but in reverse. This is why I'm in favor if exceptions for non-broken states to not be a thing or at least be optional. Making a request to an API or database and getting a successful response returning no data(or a message that says data wasn't found) means that the code and the services in the system are actually working correctly, and throwing an exception is treating the situation like a code problem when it could(and often is) simply be a data problem, which is common and often expected.

Re: You’re better off using Exceptions

#199
post #126

I wonder how many commenters clicked on this link because this really has nothing to do with "exceptions" (as in the things you raise or throw) at all. So it's a fairly terrible title that is really arguing against a catch-all Error case. The one parallel to (actual) exceptions is the author is arguing for a constrained subset of error states rather than a catch all Error type. This isn't a new idea. Java essentially…

I think Java's flavor of exceptions are especially horrible, as you mentioned a string->int parse failing is typically not exceptional at all but rather expected. However, I do think there is a place for exceptions: exceptional situations.

Status(Or) is nice for certain types of errors, but now if you want to correctly deal with out-of-memory errors that means every single function that allocates anything on the heap now needs to return a Status(Or) in case the allocation fails. That error message then needs to be propagated through your entire library back to wherever it is that you can handle memory errors, which is likely somewhere at the root of the library. That now means that every single function in your entire library needs to return a Status(Or) and propagate it, which significantly bloats your codebase.

The macros you describe likely help with that somewhat, but then those macros are basically manual exceptions in that they just unroll the stack to where you don't call the macros anymore, but they require a bunch of extra manual effort and obfuscate your code somewhat. They are also slower in the common case (no memory errors), as you are now performing an extra check on every single function call in your entire library.

Meanwhile using exceptions together with smart pointers and smart locks basically makes it so that you can handle memory errors "for free" without having to bloat your codebase. When a memory error pops up, throw an exception and unroll back to where you can properly handle the memory error. The smart pointers/smart locks/destructors will take care of cleaning up everything. No need for any extra checks all over the code base for such a rare error.

Re: You’re better off using Exceptions

#200

Earlier quoted context omitted.

If you expected the record to be found, the failure of finding it is an exception. If it was an open question, then it isn’t. This is why API generally have checks that allow developers to avoid that failure if the failure is expected (eg Record.exists). What you are suggesting is simply a reverse order (check after vs check before). I think check before leads to a much cleaner API than one that dumps a null or failu…

I don't agree. There is nothing inherently irreconcilable about a record not existing. Anyone who expects a database to always have records and that the absence of a record is an "exception" has a very strange way of thinking. It's like if a car was programmed not to start and to turn on an obnoxious alarm bell because the windshield wiper fluid is empty, and the technicians built in a jumper wire to short that circu…

>There is nothing inherently irreconcilable about a record not existing

This just isn't true. It depends on what the record is, and what state you're in (aka: CONTEXT).

incredibly clear example: 1. User logs in 2. User record no longer exists 3. Exception

That's not a recoverable situation, and the client should see that as an unexpected error.

Post reply on HN