Voting for Checked Exceptions
Yet another hideous idea from the closures camp: removing checked exceptions from the language. Now they want to remove one of the features from Java that actually works to support their pet obfuscation.
According to Neal Gafter:
We did a Google search to see how many people have written in support of checked exceptions and how many people don’t like them. The discussion seems to be lopsided against checked exceptions, but on the other hand that may be due to the fact that checked exceptions are the status quo.
For his next Google search, let me just say, I like checked exceptions and I want to keep them. The people who object to checked exceptions mostly seem not to know the difference between checked and unchecked. Most importantly, they seem not to know when to use checked exceptions and when to use unchecked exceptions. A few libraries such as the Java USB API even get this exactly backwards. And I will admit, if you don’t know this crucial piece of information, then checked exceptions seem ugly and confusing.
However, if you do understand the difference Java’s exception handling is the single best error handling and reporting mechanism ever built into a programming language. It is a strength of the language, not a weakness. To date, I don’t think any other language has come close to matching Java’s robust exception handling, and resistance to distinguishing checked from unchecked exceptions is the reason why.
I don’t have time this morning to explain the exact difference between checked and unchecked exceptions, so just go read section 8 of Effective Java, particularly items 40 and 41. In brief, checked exceptions are for unpredictable environmental conditions such as I/O errors and XML well-formedness violations while unchecked exceptions are for program failures that should be caught during testing, such as array index out of bounds or null pointers. A checked exception usually cannot be avoided by changing your code while an unchecked exception usually can be. That is, an unchecked exception normally indicates a bug in your program, and a checked exception doesn’t. That’s why we have to catch or declare checked exceptions and not runtime exceptions. A runtime exception will usually occur every time the code takes a particular path, whereas a checked exception may occur some times when a program runs through a path and not others, because checked exceptions depend on environmental conditions outside the program’s direct control. Therefore a problem that causes a runtime exception should be detected and fixed during testing, whereas a checked exception may well only appear in a customer environment. Anybody who doesn’t understand this has no business pontificating about exception handling in Java.
But please: can we take the idea of removing checked exceptions from the language off the table? They are far more important to developing reliable, comprehensible, robust code than closures ever could be. Closures are just syntax sugar that don’t let you do anything you can’t do in other ways already. Checked exceptions are a much more core feature that cannot be replaced with a little syntax sugar.
May 5th, 2010 at 11:42 pm
I think Elliotte is arguing from a theoretical perspective, but I will take it head on anyway. (And I apologize in advance if this is just a rehash of points already made in this two-year-running discussion; I free admit I read the beginning, and the end, but not the middle. However, I did at least read the article Elliotte mentioned.) The presence of checked exceptions in Java makes it impossible to express the idea that an interface can throw any exception, without resorting to ugliness. Language design is all out trade-offs, and interfaces are one the things that Java almost got right, and I’d rather have expressive interfaces than checked exceptions.
Now to step into the trenches: the ugliness is precisely because in actual practice, defensive coding in Java means that callers of an interface must guard against it throwing unchecked exceptions anyway — the caller also typically has a contract it must uphold. And as a practical matter, Elliotte’s article dealt with one rather contrived example — the caller controlled both the implementation of the interface and the data the interface is applied to. Real systems don’t have this luxury, making it impractical to use the techniques Elliotte outlined. A simple example is the simple callback interface. What are you going to do if the implementation does something that throws a RemoteException? Are you really going to make every such interface declare its own checked exception?
As for the crash-only software idea, the answer is yes, you do want a program or thread to shut down just because DNS lookup failed transiently, but not if the language is Java.
February 26th, 2012 at 11:49 am
[…] post explains that unchecked exceptions should be caught and fixed during testing […]