How to display exceptions both from catch and finally? - java

let's consider the following code:
try {
throw new Exception("from try")
} catch (Exception e) {
throw new Exception("from catch")
} finally {
throw new Exception("from finally")
}
It gives:
Exception thrown
java.lang.Exception: from finally
<...>
So it looks that finally is executed before catch and terminates execution flow.
What could I do if want to see both exceptions?

So it looks that finally is executed before catch and terminates
execution flow.
That is not correct. finally is executed after a correspondeing catch, not before. The issue is that your catch block executes, and then after that the finally block is guaranteed to execute.

This post will help you I guess:
https://stackoverflow.com/questions/3779285/exception-thrown-in-catch-and-finally-clause

Related

Exception Handling flow discrepancy

My code is below :-
class Varr {
public static void main(String[] args) {
try {
System.out.println(10/0);
}
catch(ArithmeticException e) {
System.out.println("catch1");
System.out.println("catch1");
throw new ArithmeticException ("Exce");
}
finally {
System.out.println("finally");
}
}
}
Output is :-
catch1
catch1
finally
Exception in thread "main" java.lang.ArithmeticException: Exce
at one.Varr.main(Varr.java:22)
As per my knowledge the flow has to be first try then catch and finally at last but as per the output the flow is try then few lines of catch upto the throw exception statement and then finally and the throw exception statement of catch block at last.
Why is there discrepancy in flow, I mean why finally was executed before the throw new exception statement of catch block
Because a block of finally, by definition, has to be executed no matter the outcome of the try or catch clauses.
In your case, the run-time knows there is an exception that has to be propagated upwards, but before doing so, it executes whatever is inside the finally block.
When the finally block is finished, it propagates any exception that might have been raised, or the flow continues otherwise.
You can take a look at the essentials of finally
The finally block always executes when the try block exits. This
ensures that the finally block is executed even if an unexpected
exception occurs.

Throw an exception in the finally block

I've tried to throw the same excpetion in a finally block, while the previously throwed expcetion was not catched. I expected that we have two object of Excpetion type that shal be thrown. Since we need in two catch clauses as the following:
public static void main(String[] args) {
try {
try {
try {
throw new Exception();
} finally {
System.out.println("finally");
throw new Exception();
}
} catch (Exception ex) {
System.out.println("catch");
} finally {
System.out.println("finally");
}
} catch (Exception ex) {
System.out.println("catch");
}
System.out.println("finish");
}
But that program prints:
finally
catch
finally
finish
That is, the second catch clause was not entered. Why?
When you throw an exception in the finally block, the first exception silently disappears.
It's in the JLS Chapter 14.20.2
If the finally block completes abruptly for reason S, then the try
statement completes abruptly for reason S.
This is true how ever you entered the finally block. If you entered it by throwing an exception T that exception can not be catched anymore.
When you throw an exception from the finally block, it supresses any exception thrown from the try block, therefore there was only one exception to catch.
The first catch cluase already caught that exception, so the second one had nothing to catch.
Your first try-catch is already trying to catch it, the extra try blocks aren't there for any particular reason. If you try to throw more exceptions you'll notice that you'll get a syntax error, Unreachable code
Basically, keep it in one try block

Exception Handling Java

class chain_exceptions{
public static void main(String args[]){
try
{
f1();
}
catch(IndexOutOfBoundsException e)
{
System.out.println("A");
throw new NullPointerException(); //Line 0
}
catch(NullPointerException e) //Line 1
{
System.out.println("B");
return;
}
catch (Exception e)
{
System.out.println("C");
}
finally
{
System.out.println("D");
}
System.out.println("E");
}
static void f1(){
System.out.println("Start...");
throw new IndexOutOfBoundsException( "parameter" );
}
}
I expected the Line 1 to catch the NullPointerException thrown from the Line 0 but it does not happen.
But why so ?.
When there is another catch block defined, why cant the NPE handler at Line1 catch it ?
Is it because the "throw" goes directly to the main() method ?
Catch{ . . . } blocks are associated with try{ . . . } blocks. A catch block can catch exceptions that are thrown from a try block only. The other catch blocks after first catch block are not associated with a try block and hence when you throw an exception, they are not caught. Or main() does not catch exceptions.
A kind of this for each catch block will do what you are trying to do.
try{
try
{
f1();
}
catch(IndexOutOfBoundsException e)
{
System.out.println("A");
throw new NullPointerException(); //Line 0
}
}
catch(NullPointerException e) //Line 1
{
System.out.println("B");
return;
}
The catch blocks are only for the try block. They won't catch exceptions from other catch blocks.
catch statements only catch exceptions thrown from a try { ... } block.
The NullPointerException is thrown from a catch { ... } block, not a try { ... } block.
To catch an exception thrown from a catch block you need to put another try block inside of it. Outside, wrapping the original try...catch would work, too.
A second catch doesn't catch the exception from the first catch block. You have to add another try-catch within the first catch block (or around the whole try-catch you already have) to make this run as expected.
Since java 7 you can use code below or an other option is to nest the try catch statements, there is no other option in java
try {
...
} catch( indexoutofboundsexception| nullpointerexception ex ) {
logger.log(ex);
throw ex;
}
Your catch clauses only catch exceptions thrown by f1(). They don't call exceptions thrown in other catch clauses of the same try-catch-finally construct.
Because f1() throws IndexOutOfBoundsException.
try
{
f1(); //throws IndexOutOfBoundsException
}
catch(IndexOutOfBoundsException e) //gets caught here immediately and does not check other catch blocks
{
System.out.println("A");
throw new NullPointerException(); //Line 0
}
Short answer: yes, the throw will directly throw the exception to the main method.
Generally, once a catch block is executed, it behaves like an else if, that is, it won't consider the other alternatives.
No, the reason it isn't being caught is because it isn't in the try block which is linked to the catch block. If you want to catch that exception as well, you would have to wrap the throw in a new try/catch group. The reason why you would want to do this tho, is a riddle to me.
What you also can do btw:
catch (IndexOutOfBoundsException|NullPointerException e)
This will also allow you to use the same catch block for multiple types of exceptions.
Your expectation was incorrect:
The catch blocks are associated with the try block. So once an exception is thrown inside of the try, it leaves that scope. Now you are in the scope outside the try, meaning you are no longer in any try/catch block. Any exceptions thrown here (when you re-throw) will not be caught by anything, and yes, bubble out of main.
You can not catch exception from another catch block, for that you probably need to do something like this, in your first catch block
System.out.println("A");
try{
throw new NullPointerException(); //Line 0
}
catch(NullPointerException e) //Line 1
{
System.out.println("B");
return;
}

While loop inside try block

I am trying to put a while loop inside a try /catch block. To my curiosity finally of that try catch is not executed when the while loop exits. Can some explain what is happening actually?
I tried to google, but cnould not find any details.
I assume your code looks like this:
try
{
while (...)
{
// ...
}
}
catch (FooException ex)
{
// This only executes if a FooException is thrown.
}
finally
{
// This executes whether or not there is an exception.
}
The catch block is only executed if there is an exception. The finally block usually executes whether or not an exception was thrown. So you will probably find that your finally block is actually being executed. You can prove this to yourself by placing a line there that causes some output to the console.
However there are situations in which the finally block doesn't run. See here for more details:
Does a finally block always run?
It can happen only if your program exits either by using System.exit() or if an Error or Throwable were thrown (vs. Exception that will be caught).
Try the following:
public static void main(String[] args) {
try{
System.out.println("START!");
int i=0;
while(true){
i++;
if(i > 10){
System.exit(1);
}
}
}
catch (Exception e) {
// TODO: handle exception
}
finally{
System.out.println("this will not be printed!");
}
}

Java finally block and throws exception at method level

In readFileMethod1, an IOException is explicitly catched before throwing it at the method level to ensure that the finally block is executed. However, is it neccessary to catch the exception? If I remove the catch block, shown in readFileMethod2, does the finally block get executed as well?
private void readFileMethod1() throws IOException {
try {
// do some IO stuff
} catch (IOException ex) {
throw ex;
} finally {
// release resources
}
}
private void readFileMethod2() throws IOException {
try {
// do some IO stuff
} finally {
// release resources
}
}
The finally still gets executed, regardless of whether you catch the IOException. If all your catch block does is rethrow, then it is not necessary here.
No, it's completely unnecessary to catch an exception if you're not going to do anything other than throw it.
And yes, the finally block will still be executed.
No, it isn't necessary to catch the exception unless you can't rethrow it in your method. In the code you posted the readFileMethod2 is the correct option to follow.
the finally always get executed in try catch context ... for more info check http://download.oracle.com/javase/tutorial/essential/exceptions/finally.html
finally is executed always irrespective of whether an exception is thrown or not. Only if the JVM is shut down while executing the try block or catch block, then the finally clause will not be executed. Likewise, if the thread executing the try or catch code is interrupted or killed, the finally block may not execute even though the application as a whole continues.

Categories