계산기에 숫자가 아닌 값을 입력하면 에러 메시지와 함꼐 프로그램이 그대로 종료되었다. 입력 위치에 따라 서로 다른 예외가 발생했다.
케이스 1. 첫 번째 숫자에 abc입력
첫 번째 숫자를 입력하세요 (종료하려면 exit):abc
Exception in thread "main" java.lang.NumberFormatException: For input string: "abc"
at java.base/java.lang.NumberFormatException.forInputString(...)
at java.base/java.lang.Integer.parseInt(...)
at com.example.calculator.App.main(App.java:20)
케이스 2. 두 번째 숫자에 abc 입력
첫 번째 숫자를 입력하세요 (종료하려면 exit):10
두 번째 숫자를 입력하세요:abc
Exception in thread "main" java.util.InputMismatchException
at java.base/java.util.Scanner.throwFor(...)
at java.base/java.util.Scanner.next(...)
at java.base/java.util.Scanner.nextInt(...)
at com.example.calculator.App.main(App.java:23)
계산기는 사용자가 원할 때까지 계속 동작해야 하는데, 입력 실수 한 번에 그동안 저장한 계산 기록까지 모두 날아가 버린다.
수정 전 코드
String input1 = sc.next();
// ... exit 검사 ...
int num1 = Integer.parseInt(input1); // L20 → NumberFormatException
System.out.print("두 번째 숫자를 입력하세요:");
int num2 = sc.nextInt(); // L23 → InputMismatchException
첫 번째 숫자 = next() + Integer.parseInt() : 문자열을 먼저 받고, 나중에 정수로 변환 : NumberFormatException
두 번째 숫자 = sc.nextInt() : Scanner가 읽는 순간 정수인지 검사 : InputMismatchException
첫 번째 숫자는 "exit" 입력을 처리하려고 String으로 받았기 때문에 입력 자체는 성공하고, 변환 단계에서 실패한다. 두 번째 숫자는 Scanner가 읽는 단계에서 바로 실패한다. 실패 지점이 다르니 예외 종류도 달라진 것이다.
그리고 기존 try-catch는 calculate() 호출 부분만 감싸고 있어서, 그 위에서 터진 이 두 예외는 아무도 잡지 못하고 main 밖으로 빠져나가 프로그램이 종료되었다.
입력 방식을 next() + parseInt()로 통일
두 숫자 모두 next()로 문자열을 먼저 받고, 변환은 Integer.parseInt()로 한다. next()는 입력을 항상 가져가기 때문에 버퍼에 찌꺼기가 남지 않고, 예외도 NumberFormatException 하나만 처리하면 된다.
수정 전
while(true){
System.out.print("첫 번째 숫자를 입력하세요 (종료하려면 exit):");
String input1 = sc.next();
if (input1.equalsIgnoreCase("exit")){
System.out.println("계산기를 종료합니다.");
break;
}
int num1 = Integer.parseInt(input1); // 예외 처리 없음
System.out.print("두 번째 숫자를 입력하세요:");
int num2 = sc.nextInt(); // 예외 처리 없음, 방식도 다름
System.out.print("사칙연산 기호를 입력하세요 (+, -, *, /):");
char operator = sc.next().charAt(0);
try{
int result = calculator.calculate(num1,num2,operator);
System.out.println("결과: "+result);
}catch (ArithmeticException | IllegalArgumentException e){
System.out.println(e.getMessage());
}
// ...
}
수정 후
while(true){
System.out.print("첫 번째 숫자를 입력하세요 (종료하려면 exit):");
String input1 = sc.next();
if (input1.equalsIgnoreCase("exit")){
System.out.println("계산기를 종료합니다.");
break;
}
System.out.print("두 번째 숫자를 입력하세요:");
String input2 = sc.next(); // ① 두 번째도 문자열로 받기
int num1, num2;
try {
num1 = Integer.parseInt(input1); // ② 변환을 try 안에서
num2 = Integer.parseInt(input2);
} catch (NumberFormatException e) {
System.out.println("숫자를 입력해야 합니다. 처음부터 다시 입력해주세요.");
continue; // ③ 이번 계산은 건너뛰고 처음으로
}
System.out.print("사칙연산 기호를 입력하세요 (+, -, *, /):");
char operator = sc.next().charAt(0);
try{
int result = calculator.calculate(num1,num2,operator);
System.out.println("결과: "+result);
}catch (ArithmeticException | IllegalArgumentException e){
System.out.println(e.getMessage());
}
// ...
}