[1단계] : 클래스 없이 자바의 기본 문법만을 사용하여 구현한 계산기
[2단계] : 객체 지향 개념을 적용하여 클래스 정의, 연산을 수행하는 메소드 작성한 계산기
[3단계] : 자바의 Enum, 제네릭, 람다 & 스트림을 적용한 계산기
package com.example.calculator;
import java.util.Scanner;
public class Calculator {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
System.out.println("첫 번째 숫자를 입력하세요: ");
int n = sc.nextInt();
System.out.println("두 번째 숫자를 입력하세요: ");
int m = sc.nextInt();
}
}
package com.example.calculator;
import java.util.Scanner;
public class Calculator {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
System.out.println("첫 번째 숫자를 입력하세요: ");
int n = sc.nextInt();
System.out.println("두 번째 숫자를 입력하세요: ");
int m = sc.nextInt();
System.out.println("사칙연산 기호를 입력하세요: ");
char c = sc.next().charAt(0);
}
}
package com.example.calculator;
import java.util.Scanner;
public class Calculator {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
System.out.println("첫 번째 숫자를 입력하세요: ");
int n = sc.nextInt();
System.out.println("두 번째 숫자를 입력하세요: ");
int m = sc.nextInt();
System.out.println("사칙연산 기호를 입력하세요: ");
char c = sc.next().charAt(0);
int result = 0;
switch (c) {
case '+':
result = n + m;
break;
case '-':
result = n - m;
break;
case '*':
result = n * m;
break;
case '/':
if (m == 0) {
System.out.println("나눗셈 연산에서 분모(두번째 정수)에 0이 입력될 수 없습니다");
break;
}
result = n / m;
break;
}
if (!(c == '/' && m == 0)) // 분모가 0인 나눗셈 처리
System.out.println("결과: " + result);
}
}
package com.example.calculator;
import java.util.Scanner;
public class Calculator {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
do {
System.out.println("첫 번째 숫자를 입력하세요: ");
int n = sc.nextInt();
System.out.println("두 번째 숫자를 입력하세요: ");
int m = sc.nextInt();
System.out.println("사칙연산 기호를 입력하세요: ");
char c = sc.next().charAt(0);
int result = 0;
switch (c) {
case '+':
result = n + m;
break;
case '-':
result = n - m;
break;
case '*':
result = n * m;
break;
case '/':
if (m == 0) {
System.out.println("나눗셈 연산에서 분모(두번째 정수)에 0이 입력될 수 없습니다");
break;
}
result = n / m;
break;
}
if (!(c == '/' && m == 0)) // 분모가 0인 나눗셈 처리
System.out.println("결과: " + result);
System.out.println("더 계산하시겠습니까? (exit 입력 시 종료)");
} while (!sc.next().equals("exit"));
}
}
package com.example.calculator;
import java.util.ArrayList;
import java.util.List;
public class Calculator {
// 연산 결과 저장
List<Integer> results = new ArrayList<Integer>();
public int calculate(int n, int m, char c) {
int result = 0;
switch (c) {
case '+':
result = n + m;
break;
case '-':
result = n - m;
break;
case '*':
result = n * m;
break;
case '/':
if (m == 0) {
System.out.println("나눗셈 연산에서 분모(두번째 정수)에 0이 입력될 수 없습니다");
return 0;
}
result = n / m;
break;
}
results.add(result);
return result;
}
}
package com.example.calculator;
import java.util.Scanner;
public class App {
public static void main(String[] args) {
Calculator calculator = new Calculator();
Scanner sc = new Scanner(System.in);
do {
System.out.println("첫 번째 숫자를 입력하세요: ");
int n = sc.nextInt();
System.out.println("두 번째 숫자를 입력하세요: ");
int m = sc.nextInt();
System.out.println("사칙연산 기호를 입력하세요: ");
char c = sc.next().charAt(0);
int result = calculator.calculate(n, m, c);
if (!(c == '/' && m == 0))
System.out.println("결과: " + result);
System.out.println("더 계산하시겠습니까? (exit 입력 시 종료)");
}
while (!sc.next().equals("exit"));
}
}
package com.example.calculator;
import java.util.ArrayList;
import java.util.List;
public class Calculator {
// 연산 결과 저장
private List<Integer> results = new ArrayList<Integer>();
public List<Integer> getResults() {
return results;
}
public void setResults(List<Integer> results) {
this.results = results;
}
public int calculate(int n, int m, char c) {
int result = 0;
switch (c) {
case '+':
result = n + m;
break;
case '-':
result = n - m;
break;
case '*':
result = n * m;
break;
case '/':
if (m == 0) {
System.out.println("나눗셈 연산에서 분모(두번째 정수)에 0이 입력될 수 없습니다");
return 0;
}
result = n / m;
break;
}
results.add(result);
return result;
}
}
package com.example.calculator;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
public class App {
public static void main(String[] args) {
Calculator calculator = new Calculator();
Scanner sc = new Scanner(System.in);
do {
System.out.println("첫 번째 숫자를 입력하세요: ");
int n = sc.nextInt();
System.out.println("두 번째 숫자를 입력하세요: ");
int m = sc.nextInt();
System.out.println("사칙연산 기호를 입력하세요: ");
char c = sc.next().charAt(0);
int result = calculator.calculate(n, m, c);
if (!(c == '/' && m == 0))
System.out.println("결과: " + result);
System.out.println("더 계산하시겠습니까? (exit 입력 시 종료)");
}
while (!sc.next().equals("exit"));
System.out.println("저장 된 결과값: " + calculator.getResults());
List<Integer> results = calculator.getResults();
results.add(1000);
calculator.setResults(results);
System.out.println("1000을 넣고 변경 된 결과값: " + calculator.getResults());
calculator.removeResult();
System.out.println("가장 먼저 저장된 데이터 삭제 후 변경 된 결과값: " + calculator.getResults());
}
}
package com.example.calculator;
import java.util.ArrayList;
import java.util.List;
public class Calculator {
// 연산 결과 저장
private List<Integer> results = new ArrayList<Integer>();
public List<Integer> getResults() {
return results;
}
public void setResults(List<Integer> results) {
this.results = results;
}
public int calculate(int n, int m, char c) {
int result = 0;
switch (c) {
case '+':
result = n + m;
break;
case '-':
result = n - m;
break;
case '*':
result = n * m;
break;
case '/':
if (m == 0) {
System.out.println("나눗셈 연산에서 분모(두번째 정수)에 0이 입력될 수 없습니다");
return 0;
}
result = n / m;
break;
}
results.add(result);
return result;
}
//가장 먼저 저장된 결과값 제거
public void removeResult() {
results.remove(0);
}
}
package com.example.calculator;
import java.util.InputMismatchException;
import java.util.List;
import java.util.Scanner;
public class App {
public static void main(String[] args) {
ArithmeticCalculator calculator = new ArithmeticCalculator();
Scanner sc = new Scanner(System.in);
do {
System.out.println("첫 번째 숫자를 입력하세요: ");
int n = safeNextInt(sc);
System.out.println("두 번째 숫자를 입력하세요: ");
int m = safeNextInt(sc);
System.out.println("사칙연산 기호를 입력하세요: ");
char c = safeNextChar(sc);
try {
int result = calculator.calculate(n, m, c);
System.out.println("결과: " + result);
} catch (ArithmeticException e) {
System.out.println("나눗셈 연산에서 분모(두번째 정수)에 0이 입력될 수 없습니다");
}
System.out.println("더 계산하시겠습니까? (exit 입력 시 종료)");
}
while (!sc.next().equals("exit"));
System.out.println("연산 된 결과값들: " + calculator.getResults());
List<Integer> results = calculator.getResults();
results.add(1000);
calculator.setResults(results);
System.out.println("1000을 넣고 변경 된 결과값: " + calculator.getResults());
calculator.removeResult();
System.out.println("가장 먼저 저장된 데이터 삭제 후 변경 된 결과값: " + calculator.getResults());
}
public static int safeNextInt(Scanner sc) {
while (true) {
try {
return sc.nextInt();
} catch (InputMismatchException e) {
System.out.println("[Error] 숫자를 입력해 주세요.");
sc.nextLine();
}
}
}
public static char safeNextChar(Scanner sc) {
while (true) {
try {
char c = sc.next().charAt(0);
if (c == '+' || c == '-' || c == '*' || c == '/')
return c;
else {
System.out.println("[Error] 올바른 사칙연산 기호를 입력해 주세요.");
sc.nextLine();
}
} catch (InputMismatchException e) {
System.out.println("[Error] 올바른 사칙연산 기호를 입력해 주세요.");
sc.nextLine();
}
}
}
}
package com.example.calculator;
import java.util.InputMismatchException;
import java.util.List;
import java.util.Scanner;
public class App {
public static void main(String[] args) {
ArithmeticCalculator calculator = new ArithmeticCalculator();
Scanner sc = new Scanner(System.in);
do {
System.out.println("첫 번째 숫자를 입력하세요: ");
int n = safeNextInt(sc);
System.out.println("두 번째 숫자를 입력하세요: ");
int m = safeNextInt(sc);
System.out.println("사칙연산 기호를 입력하세요: ");
OperatorType c = safeNextOperator(sc);
try {
int result = calculator.calculate(n, m, c);
System.out.println("결과: " + result);
} catch (ArithmeticException e) {
System.out.println("나눗셈 연산에서 분모(두번째 정수)에 0이 입력될 수 없습니다");
}
System.out.println("더 계산하시겠습니까? (exit 입력 시 종료)");
}
while (!sc.next().equals("exit"));
System.out.println("연산 된 결과값들: " + calculator.getResults());
List<Integer> results = calculator.getResults();
results.add(1000);
calculator.setResults(results);
System.out.println("1000을 넣고 변경 된 결과값: " + calculator.getResults());
calculator.removeResult();
System.out.println("가장 먼저 저장된 데이터 삭제 후 변경 된 결과값: " + calculator.getResults());
}
public static int safeNextInt(Scanner sc) {
while (true) {
try {
return sc.nextInt();
} catch (InputMismatchException e) {
System.out.println("[Error] 숫자를 입력해 주세요.");
sc.nextLine();
}
}
}
public static OperatorType safeNextOperator(Scanner sc) {
while (true) {
try {
char c = sc.next().charAt(0);
return OperatorType.getType(c);
} catch (Exception e) {
System.out.println("[Error] 올바른 사칙연산 기호를 입력해 주세요.");
sc.nextLine();
}
}
}
}
package com.example.calculator;
public enum OperatorType {
SUM('+'),
SUB('-'),
MUL('*'),
DIV('/');
private final char symbol;
OperatorType(char c) {
this.symbol = c;
}
public char getSymbol() {
return symbol;
}
public static OperatorType getType(char c) {
for (OperatorType type : values()) {
if (type.symbol == c) {
return type;
}
}
throw new IllegalArgumentException("[Error] 올바른 사칙연산 기호를 입력해 주세요.: " + c);
}
}
package com.example.calculator;
import java.util.ArrayList;
import java.util.List;
public class ArithmeticCalculator {
// 연산 결과 저장
private List<Integer> results = new ArrayList<Integer>();
public List<Integer> getResults() {
return results;
}
public void setResults(List<Integer> results) {
this.results = results;
}
public int calculate(int n, int m, OperatorType o) throws ArithmeticException {
int result = 0;
switch (o) {
case SUM:
result = n + m;
break;
case SUB:
result = n - m;
break;
case MUL:
result = n * m;
break;
case DIV:
try {
result = n / m;
} catch (ArithmeticException e) {
throw e;
}
break;
}
results.add(result);
return result;
}
public void removeResult() {
results.remove(0);
}
}

package com.example.calculator;
import java.util.InputMismatchException;
import java.util.List;
import java.util.Scanner;
public class App {
public static void main(String[] args) {
ArithmeticCalculator<Number> calculator = new ArithmeticCalculator<>();
Scanner sc = new Scanner(System.in);
do {
System.out.println("첫 번째 숫자를 입력하세요: ");
Number n = safeNextNumber(sc);
System.out.println("두 번째 숫자를 입력하세요: ");
Number m = safeNextNumber(sc);
System.out.println("사칙연산 기호를 입력하세요: ");
OperatorType c = safeNextOperator(sc);
try {
Number result = calculator.calculate(n, m, c);
System.out.println("결과: " + result);
} catch (ArithmeticException e) {
System.out.println("나눗셈 연산에서 분모(두번째 정수)에 0이 입력될 수 없습니다");
}
System.out.println("더 계산하시겠습니까? (exit 입력 시 종료)");
}
while (!sc.next().equals("exit"));
System.out.println("연산 된 결과값들: " + calculator.getResults());
List<Number> results = calculator.getResults();
results.add(1000);
calculator.setResults(results);
System.out.println("1000을 넣고 변경 된 결과값: " + calculator.getResults());
calculator.removeResult();
System.out.println("가장 먼저 저장된 데이터 삭제 후 변경 된 결과값: " + calculator.getResults());
}
public static Number safeNextNumber(Scanner sc) {
while (true) {
String input = sc.next();
if (isInteger(input)) {
return Integer.parseInt(input);
} else if (isDouble(input)) {
return Double.parseDouble(input);
}
System.out.println("[Error] 숫자를 입력해 주세요.");
sc.nextLine();
}
}
static boolean isInteger(String s) {
try {
Integer.parseInt(s);
return true;
} catch (NumberFormatException e) {
return false;
}
}
static boolean isDouble(String s) {
try {
Double.parseDouble(s);
return true;
} catch (NumberFormatException e) {
return false;
}
}
public static OperatorType safeNextOperator(Scanner sc) {
while (true) {
try {
char c = sc.next().charAt(0);
return OperatorType.getType(c);
} catch (Exception e) {
System.out.println("[Error] 올바른 사칙연산 기호를 입력해 주세요.");
sc.nextLine();
}
}
}
}
package com.example.calculator;
import java.util.ArrayList;
import java.util.List;
public class ArithmeticCalculator<T extends Number> {
// 연산 결과 저장
private static List<Number> results = new ArrayList<>();
public List<Number> getResults() {
return results;
}
public void setResults(List<Number> results) {
this.results = results;
}
public Number calculate(T n, T m, OperatorType o) throws ArithmeticException {
double result = calculate(n.doubleValue(), m.doubleValue(), o);
if (result % 1 == 0) {
results.add((int) result);
return (int) result;
}
results.add(result);
return result;
}
double calculate(double n, double m, OperatorType o) throws ArithmeticException {
return switch (o) {
case SUM -> n + m;
case SUB -> n - m;
case MUL -> n * m;
case DIV -> {
if (m == 0) throw new ArithmeticException("0으로 나눌 수 없습니다.");
yield n / m;
}
};
}
public void removeResult() {
results.remove(0);
}
}
String input = scanner.next();
Number num;
if(isInteger(input))
num = Integer.parseInt(input));
else if(isDouble)
num = Double.parseInt(input));
ArithmeticCalculator<Double> doubleCal;
ArithmeticCalculator<Integer> intCal;
caculate() 함수 내부에서 제네릭 타입 T끼리는 직접적인 연산이 안되는데 제네릭으로 구현하는 의미가 없는거 아닐까?
제네릭 타입끼리 연산을 위해 T 타입을 Number로 상속하고 실수로 변환하는 과정을 사용할 수 밖에 없는데,
제네릭대신 매개변수를 Number로 받아도 똑같이 동작하면 제네릭을 쓰는 의미가 없지 않을까?
입력 타입은 숫자로 고정 돼있는데 제네릭을 사용함으로 과도하게 추상화 된게 아닐까?
package com.example.calculator;
import java.util.List;
import java.util.Scanner;
public class App {
public static void main(String[] args) {
ArithmeticCalculator<Number> calculator = new ArithmeticCalculator<>();
Scanner sc = new Scanner(System.in);
do {
System.out.println("첫 번째 숫자를 입력하세요: ");
Number n = safeNextNumber(sc);
System.out.println("두 번째 숫자를 입력하세요: ");
Number m = safeNextNumber(sc);
System.out.println("사칙연산 기호를 입력하세요: ");
OperatorType c = safeNextOperator(sc);
try {
Number result = calculator.calculate(n, m, c);
System.out.println("결과: " + result);
} catch (ArithmeticException e) {
System.out.println("나눗셈 연산에서 분모(두번째 정수)에 0이 입력될 수 없습니다");
}
System.out.println("더 계산하시겠습니까? (exit 입력 시 종료)");
}
while (!sc.next().equals("exit"));
System.out.println("연산 된 결과값들: " + calculator.getResults());
System.out.println("입력된 수 보다 큰 수 조회: ");
Number input = safeNextNumber(sc);
List<Number> filter = calculator.getResults().stream().filter(num -> num.doubleValue() > input.doubleValue()).toList();
System.out.println(input + " 보다 큰 수\n" + filter);
List<Number> results = calculator.getResults();
results.add(1000);
calculator.setResults(results);
System.out.println("1000을 넣고 변경 된 결과값: " + calculator.getResults());
calculator.removeResult();
System.out.println("가장 먼저 저장된 데이터 삭제 후 변경 된 결과값: " + calculator.getResults());
}
public static Number safeNextNumber(Scanner sc) {
while (true) {
String input = sc.next();
if (isInteger(input)) {
return Integer.parseInt(input);
} else if (isDouble(input)) {
return Double.parseDouble(input);
}
System.out.println("[Error] 숫자를 입력해 주세요.");
sc.nextLine();
}
}
static boolean isInteger(String s) {
try {
Integer.parseInt(s);
return true;
} catch (NumberFormatException e) {
return false;
}
}
static boolean isDouble(String s) {
try {
Double.parseDouble(s);
return true;
} catch (NumberFormatException e) {
return false;
}
}
public static OperatorType safeNextOperator(Scanner sc) {
while (true) {
try {
char c = sc.next().charAt(0);
return OperatorType.getType(c);
} catch (Exception e) {
System.out.println("[Error] 올바른 사칙연산 기호를 입력해 주세요.");
sc.nextLine();
}
}
}
}