Java 예외를 올바르게 처리하는 방법

Java 예외를 올바르게 처리하는 방법

프로그래밍 초보자로서 개념은 예외 처리 머리를 감싸는 것이 어려울 수 있습니다. 개념 자체가 어렵다는 것이 아니라, 용어를 보면 실제보다 더 발전된 것처럼 보일 수 있습니다. 그리고 오용과 남용이 일어나기 쉬운 매우 강력한 기능입니다.





이 기사에서는 예외가 무엇인지, 왜 중요한지, 어떻게 사용하는지, 피해야 할 일반적인 실수를 배울 것입니다. 대부분의 현대 언어에는 일종의 예외 처리 기능이 있으므로 Java에서 계속 진행한다면 이러한 팁의 대부분을 사용할 수 있습니다.





자바 예외 이해하기

자바에서는 예외 응용 프로그램이 실행되는 동안 비정상적인(또는 '예외적인') 무언가가 발생했음을 나타내는 개체입니다. 그러한 예외는 던져 , 이는 기본적으로 예외 객체가 생성됨을 의미합니다(오류가 '발생'하는 방식과 유사).





아름다움은 당신이 할 수 있다는 것입니다 잡다 예외가 발생하여 비정상적인 조건을 처리하고 아무 문제가 없는 것처럼 애플리케이션이 계속 실행되도록 할 수 있습니다. 예를 들어, C의 널 포인터는 애플리케이션을 충돌시킬 수 있지만 Java를 사용하면 던지고 잡을 수 있습니다.

NullPointerException

null 변수가 충돌을 일으킬 가능성이 있기 전에 s.



예외는 객체일 뿐이지만 한 가지 중요한 특성이 있음을 기억하십시오.

Exception

클래스 또는 하위 클래스





Exception

. Java에는 모든 종류의 기본 제공 예외가 있지만 원하는 경우 고유한 예외를 만들 수도 있습니다. 일부 가장 일반적인 자바 예외 포함하다:

  • NullPointerException
  • NumberFormatException
  • IllegalArgumentException
  • RuntimeException
  • IllegalStateException

그렇다면 예외를 던지면 어떻게 될까요?





먼저 Java는 직접 메서드 내에서 발생한 예외 유형을 처리하는 코드가 있는지 확인합니다. 핸들러가 존재하지 않으면 현재 메소드를 호출한 메소드를 살펴보고 핸들이 존재하는지 확인합니다. 그렇지 않은 경우 호출한 메서드를 살펴봅니다. 저것 방법, 다음 방법 등 예외가 포착되지 않으면 애플리케이션은 스택 추적을 인쇄한 다음 충돌합니다. (실제로는 단순히 충돌하는 것보다 더 미묘한 차이가 있지만 이는 이 기사의 범위를 벗어난 고급 주제입니다.)

에게 스택 추적 Java가 예외 핸들러를 찾는 동안 통과한 모든 메소드의 목록입니다. 스택 추적은 다음과 같습니다.

Exception in thread 'main' java.lang.NullPointerException
at com.example.myproject.Book.getTitle(Book.java:16)
at com.example.myproject.Author.getBookTitles(Author.java:25)
at com.example.myproject.Bootstrap.main(Bootstrap.java:14)

우리는 이것에서 많은 것을 얻을 수 있습니다. 첫째, 던져진 예외는

NullPointerException

. 에서 발생했다

getTitle()

Book.java의 16행에 있는 메소드. 그 메서드는 다음에서 호출되었습니다.

getBookTitles()

Author.java의 25행에 있습니다. 저것 에서 호출된 메서드

main()

Bootstrap.java의 14행에 있습니다. 보시다시피, 이 모든 것을 알면 디버깅이 더 쉬워집니다.

그러나 예외의 진정한 이점은 예외를 포착하고 올바르게 설정하고 충돌 없이 응용 프로그램을 다시 시작하여 비정상적인 조건을 '처리'할 수 있다는 것입니다.

코드에서 Java 예외 사용

당신이 가지고 있다고 가정 해 봅시다

someMethod()

정수를 취하고 정수가 0보다 작거나 100보다 크면 중단될 수 있는 일부 논리를 실행합니다. 예외를 던지기에 좋은 장소가 될 수 있습니다.

어도비 미디어 인코더가 필요합니까?
public void someMethod(int value) {
if (value 100) {
throw new
IllegalArgumentException

이 예외를 잡으려면 다음 위치로 이동해야 합니다.

someMethod()

호출되어 사용 try-catch 블록 :

public void callingMethod() {
try {
someMethod(200);
someOtherMethod();
} catch (IllegalArgumentException e) {
// handle the exception in here
}
// ...
}

안에 있는 모든 것 노력하다 블록은 예외가 throw될 때까지 순서대로 실행됩니다. 예외가 발생하는 즉시 모든 후속 명령문은 건너뛰고 애플리케이션 로직은 즉시 잡다 블록.

이 예에서는 try 블록을 입력하고 즉시 호출합니다.

someMethod()

. 200은 0과 100 사이가 아니므로

IllegalArgumentException

던져진다. 이것은 즉시 실행을 종료합니다.

someMethod()

, try 블록의 나머지 논리를 건너뜁니다(

someOtherMethod()

호출되지 않음) catch 블록 내에서 실행을 재개합니다.

우리가 전화하면 어떻게 될까요?

someMethod(50)

대신에? NS

IllegalArgumentException

결코 던지지 않을 것입니다.

someMethod()

정상적으로 실행됩니다. try 블록은 다음을 호출하여 정상적으로 실행됩니다.

someOtherMethod()

someMethod()가 완료될 때. 언제

someOtherMethod()

종료되면 catch 블록을 건너뛰고

callingMethod()

계속됩니다.

try 블록당 여러 catch 블록을 가질 수 있습니다.

public void callingMethod() {
try {
someMethod(200);
someOtherMethod();
} catch (IllegalArgumentException e) {
// handle the exception in here
} catch (NullPointerException e) {
// handle the exception in here
}
// ...
}

또한 선택 사항 마지막으로 블록도 존재합니다:

public void method() {
try {
// ...
} catch (Exception e) {
// ...
} finally {
// ...
}
}

finally 블록 내의 코드는 다음과 같습니다. 언제나 상관없이 실행됩니다. try 블록에 return 문이 있으면 메서드에서 반환되기 전에 finally 블록이 실행됩니다. catch 블록에서 다른 예외를 throw하면 예외가 throw되기 전에 finally 블록이 실행됩니다.

메서드가 끝나기 전에 정리해야 하는 개체가 있는 경우 finally 블록을 사용해야 합니다. 예를 들어, try 블록에서 파일을 열고 나중에 예외가 발생한 경우 finally 블록을 사용하면 메서드를 종료하기 전에 파일을 닫을 수 있습니다.

catch 블록 없이 finally 블록을 가질 수 있습니다.

public void method() {
try {
// ...
} finally {
// ...
}
}

이렇게 하면 throw된 예외가 메서드 호출 스택을 전파하도록 허용하면서 필요한 정리를 수행할 수 있습니다(즉, 여기서 예외를 처리하고 싶지 않지만 먼저 정리해야 함).

자바에서 체크된 예외와 체크되지 않은 예외

대부분의 언어와 달리 Java는 다음을 구별합니다. 확인된 예외 그리고 확인되지 않은 예외 (예: C#에는 확인되지 않은 예외만 있습니다). 확인된 예외 ~해야하다 예외가 throw되는 메서드에서 catch되지 않으면 코드가 컴파일되지 않습니다.

확인된 예외를 만들려면 다음에서 확장하십시오.

Exception

. 확인되지 않은 예외를 생성하려면 다음에서 확장하십시오.

RuntimeException

.

확인된 예외를 throw하는 모든 메서드는 다음을 사용하여 메서드 서명에 이를 표시해야 합니다. 던지다 예어. 자바가 내장되어 있기 때문에

IOException

확인된 예외인 경우 다음 코드는 컴파일되지 않습니다.

public void wontCompile() {
// ...
if (someCondition) {
throw new IOException();
}
// ...
}

먼저 확인된 예외가 발생한다고 선언해야 합니다.

public void willCompile() throws IOException {
// ...
if (someCondition) {
throw new IOException();
}
// ...
}

메서드는 예외를 throw하는 것으로 선언될 수 있지만 실제로 예외를 throw하지 않습니다. 그렇더라도 예외는 여전히 catch해야 합니다. 그렇지 않으면 코드가 컴파일되지 않습니다.

확인되거나 확인되지 않은 예외는 언제 사용해야 합니까?

공식 Java 문서에는 이 질문에 대한 페이지 . 간결한 경험 법칙으로 차이점을 요약합니다. '클라이언트가 예외로부터 합리적으로 복구할 것으로 예상할 수 있다면 이를 확인된 예외로 만드십시오. 클라이언트가 예외에서 복구하기 위해 아무 것도 할 수 없으면 확인되지 않은 예외로 만드십시오.'

그러나 이 지침은 구식일 수 있습니다. 한편으로 확인된 예외는 더 강력한 코드를 생성합니다. 반면에 다른 언어는 Java와 같은 방식으로 예외를 검사하지 않았으며 두 가지를 보여줍니다. 하나는 기능이 다른 언어가 훔칠 만큼 유용하지 않다는 것이고, 두 번째는 Java 없이는 절대적으로 살 수 있다는 것입니다. 또한 확인된 예외는 Java 8에 도입된 람다 표현식에서 제대로 작동하지 않습니다.

Java 예외 사용 지침

예외는 유용하지만 쉽게 오용되고 남용됩니다. 다음은 혼란을 피하는 데 도움이 되는 몇 가지 팁과 모범 사례입니다.

  • 일반적인 예외보다 특정 예외를 선호합니다. 사용 |_+_| 이상 |_+_| 가능하면 |_+_|를 사용하세요. 이상 |_+_| 가능할 때.
  • 절대 잡지 마세요 |_+_| ! |_+_| 클래스는 실제로 확장됩니다 |_+_| , 그리고 catch 블록은 실제로 |_+_|와 함께 작동합니다. 또는 Throwable을 확장하는 모든 클래스. 그러나 |_+_| 클래스도 확장됩니다 |_+_| , 그리고 당신은 |_+_| 왜냐하면 |_+_| s는 심각한 복구 불가능한 문제를 나타냅니다.
  • 절대 잡지 마세요 |_+_| ! |_+_| 확장 |_+_| , 따라서 |_+_|를 잡는 모든 블록 또한 잡을 것입니다 |_+_| , 그리고 그것은 당신이 무엇을 하고 있는지 알지 못한다면 (특히 다중 스레드 응용 프로그램에서) 엉망으로 만들고 싶지 않은 매우 중요한 예외입니다. 어떤 예외를 잡아야 할지 모르겠다면 아무 것도 포착하지 않는 것이 좋습니다.
  • 디버깅을 쉽게 하려면 설명 메시지를 사용하십시오. 예외를 던질 때 |_+_| 메시지를 인수로. 이 메시지는 |__+_|를 사용하여 catch 블록에서 액세스할 수 있습니다. 예외가 잡히지 않으면 메시지도 스택 추적의 일부로 나타납니다.
  • 예외를 포착하고 무시하지 마십시오. 확인된 예외의 불편함을 피하기 위해 많은 초보자와 게으른 프로그래머는 catch 블록을 설정하지만 비워둡니다. 나쁜! 항상 우아하게 처리하십시오. 그러나 처리할 수 없는 경우 최소한 스택 추적을 인쇄하여 예외가 발생했음을 알 수 있습니다. |_+_|를 사용하여 이 작업을 수행할 수 있습니다. 방법.
  • 예외를 남용하지 않도록 주의하십시오. 망치가 있으면 모든 것이 못처럼 보입니다. 예외에 대해 처음 배울 때 대부분의 애플리케이션 제어 흐름이 예외 처리로 귀결되는 지점까지 모든 것을 예외로 바꿔야 한다는 의무감을 느낄 수 있습니다. 예외는 '예외적인' 경우를 의미한다는 것을 기억하십시오!

이제 예외가 무엇인지, 왜 사용되는지, 자신의 코드에 어떻게 통합하는지 이해할 수 있을 만큼 충분히 익숙해져야 합니다. 개념을 완전히 이해하지 못하더라도 괜찮습니다! 내 머리에서 '딸깍'하는 데 시간이 걸렸으므로 서두를 필요가 없다고 생각하지 마십시오. 천천히하세요.

질문이 있으신가요? 내가 놓친 다른 예외 관련 팁을 알고 있습니까? 아래 댓글에서 공유하세요!

공유하다 공유하다 트위터 이메일 모든 프로젝트의 데이터를 시각화하는 데이터 흐름 다이어그램을 만드는 방법

모든 프로세스의 DFD(데이터 흐름 다이어그램)는 데이터가 소스에서 대상으로 흐르는 방식을 이해하는 데 도움이 됩니다. 만드는 방법은 다음과 같습니다.

다음 읽기
관련 항목
  • 프로그램 작성
  • 자바
저자 소개 조엘 리(1524개의 기사 출판)

Joel Lee는 2018년부터 MakeUseOf의 편집장입니다. 그는 학사 학위를 받았습니다. 컴퓨터 과학 및 9년 이상의 전문적인 글쓰기 및 편집 경험.

가사가 있는 노래방 노래 무료 다운로드
조엘 리가 참여한 작품 더보기

뉴스레터 구독

뉴스레터에 가입하여 기술 팁, 리뷰, 무료 전자책 및 독점 거래를 확인하십시오!

구독하려면 여기를 클릭하세요.