[java] try-finally와 try-catch의 차이점

차이점은 무엇입니까

try {
    fooBar();
} finally {
    barFoo();
}

try {
  fooBar();
} catch(Throwable throwable) {
    barFoo(throwable); // Does something with throwable, logs it, or handles it.
}

Throwable에 대한 액세스를 제공하기 때문에 두 번째 버전이 더 좋습니다. 두 변형 사이에 논리적 차이나 선호하는 규칙이 있습니까?

또한 finally 절에서 예외에 액세스하는 방법이 있습니까?



답변

다음은 두 가지입니다.

  • catch 블록은 try 블록에서 예외가 발생하는 경우에만 실행됩니다.
  • finally 블록은 예외가 발생하거나 발생하지 않는 경우 항상 try (-catch) 블록 다음에 실행됩니다.

귀하의 예에서 세 번째 가능한 구성을 표시하지 않았습니다.

try {
    // try to execute this statements...
}
catch( SpecificException e ) {
    // if a specific exception was thrown, handle it here
}
// ... more catches for specific exceptions can come here
catch( Exception e ) {
    // if a more general exception was thrown, handle it here
}
finally {
    // here you can clean things up afterwards
}

그리고 @codeca가 그의 코멘트에서 말했듯이, finally 블록은 예외가 없어도 실행되기 때문에 finally 블록 내에서 예외에 접근 할 수있는 방법이 없습니다.

물론 블록 외부에서 예외를 보유하는 변수를 선언하고 catch 블록 내부에 값을 할당 할 수 있습니다. 나중에 finally 블록 내에서이 변수에 액세스 할 수 있습니다.

Throwable throwable = null;
try {
    // do some stuff
}
catch( Throwable e ) {
    throwable = e;
}
finally {
    if( throwable != null ) {
        // handle it
    }
}


답변

이것들은 변형이 아니라 근본적으로 다른 것들입니다. finally실행 항상 , catch예외가 발생하는 경우에만 사용할 수 있습니다.


답변

마지막으로 catch 블록은 매우 다릅니다.

  • catch 블록 내에서 throw 된 예외에 응답 할 수 있습니다. 이 블록 은 처리되지 않은 예외가 있고 유형이 catch 블록의 매개 변수에 지정된 유형과 일치하거나 하위 클래스 인 경우에만 실행됩니다 .
  • 마지막으로 예외가 발생했는지 여부에 관계없이 try 및 catch 블록 후에 항상 실행됩니다 .

그래서

try {
  //some code
}
catch (ExceptionA) {
  // Only gets executed if ExceptionA 
  // was thrown in try block
}
catch (ExceptionB) {
  // Only executed if ExceptionB was thrown in try 
  // and not handled by first catch block
}

~와 다르다

try {
  //some code
}
finally {
  // Gets executed whether or not 
  // an exception was thrown in try block
}

상당히.

try 블록을 정의하는 경우 정의해야합니다.

  1. 마지막으로 블록 하나, 또는
  2. 하나 이상의 캐치 블록 또는
  3. 하나 이상의 catch 블록과 하나의 finally 블록

따라서 다음 코드도 유효합니다.

try {
  //some code
}
catch (ExceptionA) {
  // Only gets executed if 
  // ExceptionA was thrown in try block
}
catch (ExceptionB) {
  // Only executed if ExceptionB was thrown in 
  // try and not handled by first catch block
}
//even more catch blocks
finally {
  // Gets executed whether or not an 
  // exception was thrown in try block
}


답변

try 예외를 발생시킬 수있는 메소드를 실행하는 데 사용됩니다.

catch 해당 예외를 “잡기”하는 데 사용됩니다.

finally 잡힌 예외에서 필요한 정리에 사용됩니다.

try{
    myObject.riskyMethod(); // run a method that may throw an exception
}
catch(Exception ex){
    myLogger.log(ex.Message); // "catch" stop that exception
}
finally{
    myObject = null; // clean up needed from that exception being caught
}


답변

try {
    statements;
} catch (exceptionType1 e1) {      // one or multiple
    statements;
} catch (exceptionType2 e2) {
    statements;
}
...
} finally {                                 // one or none
    statements;
}
  1. 모든 try 문은 하나의 catch 절 또는 finally 절을 포함해야합니다.
  2. 여러 catch 절을 가질 수 있지만 finally 절은 하나만 있습니다.
  3. 실행 중에 오류가 발생하면 Control이 해당 Catch 블록으로 전송되어 명령문을 실행하고 finally 블록이 실행됩니다.

마지막으로 블록은 항상 실행되므로 일반적으로 마지막 블록이 사용되며 세션, 데이터베이스 연결 또는 파일 또는 소켓이 열려있을 때 해당 연결을 닫는 코드가 배치됩니다. 이것은 응용 프로그램에서 메모리 누수 나 다른 문제가 발생하지 않도록하기위한 것입니다.


답변

마지막으로 catch 블록은 매우 다릅니다.

catch 블록 내에서 throw 된 예외에 응답 할 수 있습니다. 이 블록은 처리되지 않은 예외가 있고 유형이 catch 블록의 매개 변수에 지정된 유형과 일치하거나 하위 클래스 인 경우에만 실행됩니다. 마지막으로 예외가 발생했는지 여부에 관계없이 try 및 catch 블록 후에 항상 실행됩니다.


답변

내 연구에서 마지막으로 블록은 항상 실행되며 주로 “열려있는 모든 연결이 닫히고”불필요하게 실행중인 것을 파괴하는 데 사용됩니다.