Live data from Hacker News

Why checked exceptions failed

borretti.me

21–30 of 318 posts

Re: Why checked exceptions failed

#21

I have extensive experience in C# as well as Java. It is bizarre to suggest that checked exceptions have failed. It is unchecked exceptions that have failed. It is the biggest flaw of C#, in fact. Why? As an example, I wrote some very good C# code, carefully tested it, made it work flawlessly, then suddenly it started crashing. What happened? Someone made a change in a function I was calling, and it started throwing…

> Someone made a change in a function I was calling, and it started throwing a new exception.

If it has nothing to do with your code, why not either let it bubble up the stack or try/finally it to do whatever clean-up you need to do before re-throwing it and letting it move on to a global logger or similar.

If it is something you care about you can always catch the specific exception type and handle it.

Maybe whoever worked on the other function wasn't even aware it might throw that particular exception.

Granted I am far more experienced in C# than Java, but the idea that with every code change you potentially have to review and declare every single type of exception seems like madness ("what happens if we pull the cord when it's here, what type will that throw?").

Re: Why checked exceptions failed

#22

I have extensive experience in C# as well as Java. It is bizarre to suggest that checked exceptions have failed. It is unchecked exceptions that have failed. It is the biggest flaw of C#, in fact. Why? As an example, I wrote some very good C# code, carefully tested it, made it work flawlessly, then suddenly it started crashing. What happened? Someone made a change in a function I was calling, and it started throwing…

Catching the root exception is not a bad idea. If you had caught the new exception what would you have done with it? Most of the time, it’s either catch the exception, log it in a central logging system keep moving and have a central alerting system or catch the exception log it and crash the program.

Catching at the root is only half of story. You must also have ability to resume where it was thrown.

Re: Why checked exceptions failed

#23
post #17

Checked exceptions are great. But they were abandoned due to the functional paradigm so now it’s cumbersome to use them. Errors should be first class of any language and not bolted on as some sort of afterthought, language or design. Errors are something that occurs in real life and should be handled as such. Unchecked errors are a pain to deal with and always are unexpected which you need to dig into the code to see…

They were abandoned long before “the functional paradigm”. They started being a problem when the Java community decided interactions should go through interfaces over concrete types, and it only got worse with genetics then functional streams.

Re: Why checked exceptions failed

#24

My opinion is the exact opposite see https://debugagent.com/everything-bad-in-java-is-good-for-yo... Checked exceptions are unpopular since no one likes responsibility. But they are great when used right. Calls that must have proper cleanup after them e.g. SQL, IO are checked. The fact that this must be communicated via interfaces is hugely important. There are "weird" problems such as stream close() throwing a check…

> Calls that must have proper cleanup after them e.g. SQL, IO are checked. Why? In C# you use a “using” block and whether your code exits the using block successfully or with an exception, the cleanup is automatic. RAII has been around at least since the 80s with C++.

We have it in Java too. For us it's try-with-resources and has nothing to do with checked exceptions. Checked exceptions remind you that you need to wrap the code and need to take that into account.

They also force you to declare that an exception is thrown if you don't want to handle it in the current method. That's important as the signature of the method carries an important failure that can't be dismissed and is enforced by the compiler.

Re: Why checked exceptions failed

#25

My opinion is the exact opposite see https://debugagent.com/everything-bad-in-java-is-good-for-yo... Checked exceptions are unpopular since no one likes responsibility. But they are great when used right. Calls that must have proper cleanup after them e.g. SQL, IO are checked. The fact that this must be communicated via interfaces is hugely important. There are "weird" problems such as stream close() throwing a check…

> Calls that must have proper cleanup after them e.g. SQL, IO are checked. Why? In C# you use a “using” block and whether your code exits the using block successfully or with an exception, the cleanup is automatic. RAII has been around at least since the 80s with C++.

This is what try-with-resource does in Java. Introduced in Java 8 I think so better late than never

Re: Why checked exceptions failed

#26

I have extensive experience in C# as well as Java. It is bizarre to suggest that checked exceptions have failed. It is unchecked exceptions that have failed. It is the biggest flaw of C#, in fact. Why? As an example, I wrote some very good C# code, carefully tested it, made it work flawlessly, then suddenly it started crashing. What happened? Someone made a change in a function I was calling, and it started throwing…

Why not catch System.Exception also? Or just catch

Re: Why checked exceptions failed

#27
post #9

The issue with all exceptions, and error handling in general, is that only very rarely is there actually recourse for an error. For instance, in an HTTP request handler, the vast majority of errors will end up as something like a 500. Checked exceptions are annoying because they make you explicitly handle an error when you likely already have a handler in place to handle all exceptions, checked or otherwise.

Exactly, the boilerplate overhead isn't worth it when 95% of times you don't have anything meaningful to do with the exception but let it propagate.

Re: Why checked exceptions failed

#28
As others have mentioned, an interface is a contract and any possible exception that may be thrown needs to be explicitly defined, that's why checked exceptions exists.

However, there is an exception (pun intended) to this: inline lambdas. You can use lambdas as variables, pass them as parameters, etc. And it makes sense for them to retain the interface if needed, but (at least on java) when you are doing a .map(v->parseInt(v)) checked exceptions can't escape the lambda, and that's probably the worst problem of java lambdas.

You can avoid this with custom interfaces where the exception is a generic parameter, but sadly native ones aren't defined like this (yes, exceptions that a function throws can also be defined with generics, and the compiler will automatically use the more restrictive of the lambda code! )

Re: Why checked exceptions failed

#29
Little aside, but I feel a lot of the drama surrounding exception could have been solved with a little syntactic sugar making their handling easier. Something along the lines of Perl's "|| die("...")" pattern would be a start (i.e. add some context and rethrow).

In C++ I find it quite infuriating that try{} opens up a new lexical scope, which means you can't construct something, check for errors and move on, since the act of adding a try{} means you'd call the destructor of the thing you just constructed. Meanwhile surrounding a whole block of code with a try{} means you no longer can tell where the exception came from.

Re: Why checked exceptions failed

#30

I have extensive experience in C# as well as Java. It is bizarre to suggest that checked exceptions have failed. It is unchecked exceptions that have failed. It is the biggest flaw of C#, in fact. Why? As an example, I wrote some very good C# code, carefully tested it, made it work flawlessly, then suddenly it started crashing. What happened? Someone made a change in a function I was calling, and it started throwing…

Catching the root exception is not a bad idea. If you had caught the new exception what would you have done with it? Most of the time, it’s either catch the exception, log it in a central logging system keep moving and have a central alerting system or catch the exception log it and crash the program.

> Catching the root exception is not a bad idea. If you had caught the new exception what would you have done with it?

Something relevant to the error condition, probably?

There may be some cases where the total set of possible errors is too large to meaningfully handle every one of them specifically (for instance if you call a high level GPU initialization routine that can fail in a myriad of ways) but that's not true in all cases. Maybe the new error was in fact recoverable, or maybe it calls for some more specific diagnostics.

At any rate I completely agree with the parent that changing the set throwable exceptions should be considered a breaking API change and should be enforced by the compiler. If an API method wants to future-proof and be able to throw anything, it can declare just that and everybody will know to expect the unexpected.

That's why I vastly prefer Rust's Result system which does most of what exceptions do and with fairly similar ergonomics but with normal return values and all the type checking that it involves.

Post reply on HN