Over a million developers have joined DZone.
{{announcement.body}}
{{announcement.title}}

Would We Still Criticize Checked Exceptions, If Java Had a Better Try-Catch Syntax?

DZone's Guide to

Would We Still Criticize Checked Exceptions, If Java Had a Better Try-Catch Syntax?

Exception handling is a necessary part of life for developers, especially in the Java world. Checked exceptions seem to bear the brunt of criticism in that world, but would that still be the case if Java had better syntax for exception handling?

· Java Zone
Free Resource

Microservices! They are everywhere, or at least, the term is. When should you use a microservice architecture? What factors should be considered when making that decision? Do the benefits outweigh the costs? Why is everyone so excited about them, anyway?  Brought to you in partnership with IBM.

In the context of a previous blog post about JUnit 5, Maaartinus, one of our readers, has brought up a very interesting idea:

The only problem with try-catch is its verbosity, which is something I can live with (IMHO a lone catch would do better, the implicit try would apply to all preceding code in the block; just syntactic sugar)

Huh!

Imagine a world where the following is valid Java code:

{
 something();
}
catch (Exception e) {
 /* All exceptions from the above block */
}

Likewise:

{
 something();
}
finally {
 /* Clean up after the previous block */
}

In other languages, this is implemented exactly as such. Take PL/SQL, for instance. An ordinary block looks like this:

BEGIN
 SOMETHING();
END;

Replace curly braces by BEGIN and END keywords, and you have exactly the same thing. Now, if SOMETHING raises an exception, in PL/SQL, we can append an EXCEPTION block, which does exactly the same thing as catch in Java:

BEGIN
 SOMETHING();
EXCEPTION
 WHEN OTHERS THEN NULL;
END;

Indeed, in these very trivial cases, the try keyword seems optional just like there is no such keyword in PL/SQL, and we don’t really need it as the scope of the catch and/or finally blocks is very well defined (at first sight, there might be caveats, of course).

So What? We’ve Saved Three Characters…

In these trivial cases, we’re not gaining a lot from the “improved” syntax. But what about many other cases where the notoriously verbose try { ... } catch { ... } syntax might be getting on our nerves…? Again, in PL/SQL, whenever you’re using a block using BEGIN .. END, you can automatically profit from optionally adding an EXCEPTION block.

Without thinking this through thoroughly though (whew, some English language usage!), this could add immense syntactic value to Java. For instance:

Lambdas

// Better:
Consumer<String> consumer = string -> {
 something();
}
catch (Exception e) {
 /* still part of the consumer */
}

// Instead of:
Consumer<String> consumer = string -> {
 try {
 something();
 }
 catch (Exception e) {
 /* still part of the consumer */
 }
}

Would that have prevented long discussions about checked exceptions in lambdas and in the Stream API

Loops

// Better:
for (String string : strings) {
 something();
}
catch (Exception e) {
 /* still part of the loop's iteration */
}

// Instead of:
for (String string : strings) {
 try {
 something();
 }
 catch (Exception e) {
 /* still part of the loop's iteration */
 }
}

Again, tons of syntactic value here!

If / Else

For consistency reasons, although this might appear a bit esoteric to people used to Java code. But let’s think out of the box, and admit the following!

// Better:
if (check) {
 something();
}
catch (Exception e) {
 /* still part of the if branch */
}
else {
 somethingElse();
}
catch (Exception e) {
 /* still part of the else branch */
}

// Instead of:
if (check) {
 try {
 something();
 }
 catch (Exception e) {
 /* still part of the if branch */
 }
}
else {
 try {
 something();
 }
 catch (Exception e) {
 /* still part of the else branch */
 }
}

Huh!

Method Bodies

Last but not least, method bodies would be the ultimate entities profiting from this additional syntax sugar. If you’re admitting that the curly braces in methods are nothing but mandatory blocks (or mandatory BEGIN .. END constructs), then you could have:

// Better:
public void method() {
 something();
}
catch (Exception e) {
 /* still part of the method body */
}

// Instead of:
public void method() {
 try {
 something();
 }
 catch (Exception e) {
 /* still part of the method body */
 }
}

This is particularly useful for (static) initialisers, where exception handling is always a pain, as there is no way to specify a throws clause in a (static) initialiser (might be a good opportunity to fix that!)

class Something {

 // Better:
 static {
 something();
 }
 catch (Exception e) {
 /* still part of the initialiser body */
 }

 // Instead of:
 static {
 try {
 something();
 }
 catch (Exception e) {
 /* still part of the initialiser body */
 }
 }
}

Of course, the “old” syntax would still be possible. For instance, when using the try-with-resources statement, it is inevitable. But the big advantage of such syntax sugar is that in cases when we have to handle exceptions (namely checked exceptions), the pain would be lessened a bit, as we could do so without nesting blocks several levels deep. Perhaps, with this syntax, we would no longer criticise checked exceptions at all?

Very interesting ideas, thanks again, Maaartinus, for sharing.

What are your thoughts?

Discover how the Watson team is further developing SDKs in Java, Node.js, Python, iOS, and Android to access these services and make programming easy. Brought to you in partnership with IBM.

Topics:
exception handling ,java ,syntax ,exceptions

Published at DZone with permission of Lukas Eder, DZone MVB. See the original article here.

Opinions expressed by DZone contributors are their own.

The best of DZone straight to your inbox.

SEE AN EXAMPLE
Please provide a valid email address.

Thanks for subscribing!

Awesome! Check your inbox to verify your email so you can start receiving the latest in tech news and resources.
Subscribe

{{ parent.title || parent.header.title}}

{{ parent.tldr }}

{{ parent.urlSource.name }}