Java - Difference between throwing an exception and catching and rebuilding an exception

I am confused by the fact that it would be beneficial to catch and reconstruct the exception, and just throw it first.

for instance

private void testMethod() throws Exception { //some bad code here } 

against

 private void testMethod() throws Exception { try { //some bad code here } catch (Exception e) { throw e; } } //end testMethod() 

Does the stack trace of the error message persist? I tried to create an example, but did not see another way between them.

Thanks for the help.

+4
source share
7 answers

There is no difference in behavior between the two code samples. (In particular, stacktraces are written when an exception is thrown, and not when it is thrown, so the restored exception will still have the original stack trace). Usually people use a simpler idiom.

This does not mean that re-construction does not have its goals. For example, if you want to handle all exceptions except FooBarExceptions, you can write:

 try { // bad code } catch (FooBarException e) { throw e; } catch (Exception e) { e.printStackTrace(); } 

Or if the decision to handle the exception is more active than just checking its type, you can simply catch it and reconstruct it if it turns out that you cannot handle it:

 for (int attempts = 0; attemps < 6; attempts++) { try { return crankyMethod(); } catch (Exception e) { if (fatal(e)) { throw e; } else { // try again continue; } } } 

It is worth noting that when people talk about retreating, some of them want to throw another exception, as in the following example:

 for (int i = 0; i < array.length; i++) { try { process(array[i]); } catch (Exception e) { throw new RuntimeException("Could not process element at index " + i, e); } } 

The advantage of this pattern is to decorate the original exception with additional information that may be relevant (in the example above: what data cannot be processed). Note that the original exception is passed to the constructor of the new one, so its stack trace is not lost.

+5
source

As others have said, there is no difference in your example, and the second form should be avoided.

The only place this sometimes makes sense is where you need to catch some exceptions and let others rush up. Since Java exception handling syntax is limited, sometimes you can do this:

 try { somePieceOfCode(); } catch( RuntimeException e ) { throw e; } catch( Exception e ) { handleException(e); } 

This is sometimes done if somePieceOfCode throws several different marked exceptions that do not have a common base class (except for Exception ), but should be handled the same way. You might not want to just catch an Exception , because it will catch things like NullPointerException as well, and you might prefer to bubble up as it is.

This code will allow RuntimeExceptions bubbles up, but handle all other exceptions.

This idiom is a little unusual, and not everyone likes it, but you can see it in some places.

+2
source

With this approach, you can change the Exception. For example, you could give it a more specific message.

With this in mind, you should usually not use this technique because

  • It clusters your code without any additional benefits (under normal circumstances).
  • You should only use try-catch blocks, which are really necessary, because this can slow down the execution.
+1
source

The standard reasons for exclusion and re-exclusion are:

  • To register an incident and an exception.
  • Perform some cleanup due to an exception (but often better done in the finally block).
  • To wrap the exception in a more appropriate exception (for example, it is more likely that your processAccount () method is likely to use an AccountException (or some similar one) instead of a DbException).
+1
source

There is no difference. If you do not want to do something with it (exception), before throwing it away again.

0
source

I do not think that there is a big difference, but for what it costs, I would prefer the first.

You should not catch an exception if you cannot do something with it or if your class is the boundary beyond which no exception should propagate (for example, a web controller that catches all exceptions and router users to friendly error pages).

Just catching and remodeling is a waste of the keys. He does not add any information and does nothing constructive.

The only exception is to catch the checked exception and wrap it as an excluded exception. Otherwise, avoid the second idiom.

0
source

One of the main advantages of catching and then re-creating is wrapping the exceptions in another exception for a specific domain, so the calling code does not need to worry about specific implementation problems and can simply catch a specific library exception.

There is no real benefit in the above example, however a good example of such an advantage can be seen in other libraries - as an example, we can look at Hibernate.

Hibernate catches a generic SQLException, and then examines the object to determine the real cause of the exception, before wrapping it in a Hibernate exception, which more describes what the problem was in the first place.

However, if you just catch the exception and throw the same exception, then you will most likely do so so that you can catch the exception first (although this is not necessarily the best approach to use).

0
source

Source: https://habr.com/ru/post/1400312/


All Articles