[java] throws 선언을 추가하지 않고 예외를 throw하는 방법이 있습니까?

나는 다음과 같은 상황이 있습니다.

다른 기본 클래스에서 상속하고 메서드를 재정의하는 Java 클래스가 있습니다. 기본 메서드는 예외를 throw하지 않으므로 throws ...선언 이 없습니다 .

이제 내 자신의 방법이 예외를 throw 할 수 있어야하지만 선택권이 있습니다.

  • 예외를 삼켜 라
  • throws 선언 추가

첫 번째는 예외를 자동으로 무시하고 (몇 가지 로깅을 수행 할 수 있음) 두 번째는 다른 메서드 헤더로 인해 컴파일러 오류를 생성하므로 둘 다 만족스럽지 않습니다.

public class ChildClass extends BaseClass {

        @Override
        public void SomeMethod() {
            throw new Exception("Something went wrong");
        }
}



답변

정말로 원한다면 선언하지 않고도 확인되지 않은 예외를 던질 수 있습니다. 확인되지 않은 예외는 RuntimeException. 확장 Error되는 Throwables 도 확인되지 않지만 완전히 처리 할 수없는 문제 (예 : 유효하지 않은 바이트 코드 또는 메모리 부족)에만 사용해야합니다.

특정 경우에 Java 8 UncheckedIOException은 래핑 및 다시 던지기를 위해 추가되었습니다 IOException.


답변

다음은 트릭입니다.

class Utils
{
    @SuppressWarnings("unchecked")
    private static <T extends Throwable> void throwException(Throwable exception, Object dummy) throws T
    {
        throw (T) exception;
    }

    public static void throwException(Throwable exception)
    {
        Utils.<RuntimeException>throwException(exception, null);
    }
}

public class Test
{
    public static void main(String[] args)
    {
        Utils.throwException(new Exception("This is an exception!"));
    }
}


답변

세 번째 옵션은 예외 검사를 옵트 아웃하고 (표준 API 자체가 가끔 수행해야하는 것처럼) 확인 된 예외를 다음과 같이 래핑하는 것입니다 RuntimeException.

throw new RuntimeException(originalException);

보다 구체적인 하위 클래스를 사용할 수 있습니다 RuntimeException.


답변

순전히 FYI 로 대체 답변을 추가하고 싶습니다. .

예, 클래스 throws를 사용하여 선언 을 추가하지 않고 확인 된 예외를 throw하는 방법이 sun.misc.Unsafe있습니다. 이는 다음 블로그 게시물에 설명되어 있습니다.

선언하지 않고 메서드에서 확인 된 예외를 throw합니다.

샘플 코드 :

public void someMethod() {
  //throw a checked exception without adding a "throws"
  getUnsafe().throwException(new IOException());
}

private Unsafe getUnsafe() {
  try {
    Field field = Unsafe.class.getDeclaredField("theUnsafe");
    field.setAccessible(true);
    return (Unsafe) field.get(null);
  } catch (Exception e) {
    throw new RuntimeException(e);
  }
}

그러나 이것은 권장되지 않습니다. 다른 답변 중 일부에 설명 된대로 확인되지 않은 예외로 래핑하는 것이 좋습니다.


답변

확인되지 않은 예외를 던지지 않는 이유는 무엇입니까? 이것은 선언 할 필요가 없습니다.

두 가지 대안은

  • 확인되지 않은 예외로 확인 된 예외로 래핑합니다.
  • 컴파일러에게 확인 된 예외를 던지고 있음을 알리지 마십시오. 예 : Thread.currentThread (). stop (e);
  • Java 6에서는 예외가 발생한 경우 다시 throw 할 수 있습니다. final 있으며 컴파일러는 어떤 확인 된 예외를 포착했는지 알고 있습니다.
  • Java 7에서 예외가 사실상 최종적인 경우, 즉 코드에서 변경하지 않으면 예외를 다시 던질 수 있습니다.

나중에 코드에서 검사 예외를 발생시키고 호출 코드에서이를 포착 할 때 더 유용하지만 그 사이의 계층은 예외에 대해 아무것도 알지 못합니다.


답변

예, 이유가 있지만 전혀 사용하지 않는 것이 좋습니다.

자바 안전하지 않은 패키지

getUnsafe().throwException(new IOException());

이 메서드는 확인 된 예외를 throw하지만 코드에서이를 포착하거나 다시 throw하지 않습니다. 런타임 예외와 같습니다.


답변

다음은 확인 된 예외를 가로 채서 확인되지 않은 예외로 래핑하는 예입니다.

public void someMethod() {
   try {
      doEvil();
   }
   catch (IOException e)
   {
       throw new RuntimeException(e);
   }
}