메서드는 문제없이 수행됐지만, 어떤 객체를 이상한 상태로 만들어놓아서 미래의 알 수 없는 시점에이 메서드와는 관련 없는 오류를 낼 수 있다.
매개변수 검사에 실패하면 실패 원자성을 어기는 결과를 낳을 수 있다.(아이템 76)
호출된 메서드가 실패해도 해당 객체는 메서드 호출 전 상태를 유지하는 특성을 실패 원자적이라고 한다
예외의 문서화
public과 protected 메서드는 매개변수 값이 잘못됐을 때 던지는 예외를 문서화해야 한다.
@throws 자바독 태그를 사용하면 된다.
일반적으로 IllegalArgumentException, IndexOutOfBoundsException, NullPointerException 중 하나가 될 것이다.
제약을 문서화한다면 어겼을 때 발생하는 예외도 함께 기술해야한다.
예외의 문서화 예시
// BigInteger 클래스에 구현되어있음
/**
Returns a BigInteger whose value is {@code (this mod m}). This method
differs from {@code remainder} in that it always returns a
non-negative BigInteger.
@param m the modulus.
@return {@code this mod m}
@throws ArithmeticException {@code m} ≤ 0
@see #remainder
*/
public BigInteger mod(BigInteger m) {
if (m.signum <= 0)
throw new ArithmeticException("BigInteger: modulus not positive");
BigInteger result = this.remainder(m);
return (result.signum >= 0 ? result : result.add(m));
}
@throws태그에 0보다 작거나 같은 값의 나머지를 구하려 하면, ArithmeticException이 발생한다고 알려주고 있다.
null 검사
자바 7에 추가된 java.util.Objects.requireNonNull메서드는 유연하고 사용하기 편하니, 더 이상 null검사를 수동으로 하지 않아도 된다.
public class Main {
public static void main(String[] args) {
String str = "Hello, world!";
printStringLength(str); // 정상적인 문자열을 전달
String nullStr = null;
printStringLength(nullStr); // null을 전달
}
public static void printStringLength(String str) {
// java.util.Objects.requireNonNull을 사용하여 null 검사
String input = java.util.Objects.requireNonNull(str, "문자열은 null일 수 없습니다.");
// 문자열의 길이를 출력
System.out.println("입력된 문자열의 길이: " + input.length());
}
}
필요한 곳 어디서든 순수한 null 검사 목적으로 사용해도된다.
assert
public이 아닌 메서드라면 단언문(assert)을 사용해 매개변수 유효성을 검증할 수 있다.
public class Main {
public static void main(String[] args) {
// long[] arr = {5, 2, 7, 3, 9, 1};
// int offset = 2;
// int length = 4;
long[] arr = null;
int offset = -1;
int length = 5;
sort(arr, offset, length);
for (int i = offset; i < offset + length; i++) {
System.out.print(arr[i] + " ");
}
}
private static void sort(long a[], int offset, int length) {
assert a != null;
assert offset >= 0 && offset <= a.length;
assert length >= 0 && length <= a.length - offset;
for (int i = offset; i < offset + length - 1; i++) {
int minIndex = i;
for (int j = i + 1; j < offset + length; j++) {
if (a[j] < a[minIndex]) {
minIndex = j;
}
}
long temp = a[minIndex];
a[minIndex] = a[i];
a[i] = temp;
}
}
}
assert에서 실패하면 AssertionError이 발생한다.
런타임에 아무런 효과도, 성능 저하도 없다. (debugging할때 사용)
java를 실행할 때 명령줄에서 -ea 혹은 --enableassertions 플래그를 설정해서 확인할수있다.
Chapter : 8. 메서드
Item : 49. 매개변수가 유효한지 검사하라
Assignee : byunghyunkim0
🍑 서론
메서드와 생성자 대부분은 입력 매개변수의 값이 특정 조건을 만족하기를 바란다.
이런 제약은 반드시 문서화해야 하며 메서드 몸체가 시작되기 전에 검사해야한다.
🍑 본론
매개변수 검사에서 생기는 문제
예외의 문서화
public과 protected 메서드는 매개변수 값이 잘못됐을 때 던지는 예외를 문서화해야 한다.
IllegalArgumentException
,IndexOutOfBoundsException
,NullPointerException
중 하나가 될 것이다.예외의 문서화 예시
BigInteger result = this.remainder(m); return (result.signum >= 0 ? result : result.add(m)); }
@throws
태그에 0보다 작거나 같은 값의 나머지를 구하려 하면,ArithmeticException
이 발생한다고 알려주고 있다.null 검사
자바 7에 추가된
java.util.Objects.requireNonNull
메서드는 유연하고 사용하기 편하니, 더 이상 null검사를 수동으로 하지 않아도 된다.assert
public이 아닌 메서드라면 단언문(assert)을 사용해 매개변수 유효성을 검증할 수 있다.
java를 실행할 때 명령줄에서 -ea 혹은 --enableassertions 플래그를 설정해서 확인할수있다.
나중에 쓰려고 저장하는 매개변수의 유효성을 검사하라
Objects.requiereNonNull
을 이용해 null검사를 수행한다.유효성 검사 예외
ClassCastException
을 던진다.🍑 결론
매개변수들에 어떤 제약이 있을지 생각해고 문서화하고 명시적으로 검사해라
Referenced by
https://blueyikim.tistory.com/2452