diff --git a/README.md b/README.md index fcf3f057..c6888683 100644 --- a/README.md +++ b/README.md @@ -5,3 +5,30 @@ ## 과제 제출 과정 * [과제 제출 방법](https://github.com/next-step/nextstep-docs/tree/master/ent-precourse) + + +## 메소드 구현 설명 +### 1. void setAnswer() +- 컴퓨터가 정한 임의의 정답인 answer 배열을 초기화하는 메소드 +### 2. void setGuess(int inputNumber) +- 플레이어가 맞추어야 할 정답인 guess 배열을 초기화하는 메소드 +- inputNumber를 슬라이싱하여 세 자리수를 만들어 guess를 초기화한다. +### 3. int checkSingleDigit(int idx) +- guess 의 idx 번째 숫자를 확인하여 볼, 스트라이크 여부를 확인하는 메소드 +- 스트라이크라면 10를 리턴한다. +- 볼이라면 1을 리턴한다. +- 둘 다 아니라면 0을 리턴한다. +### 4. boolean checkGuess() +- 0, 1, 2를 각각 checkNumber() 메소드의 arg 로 넣어 리턴값을 모두 result 변수에 넣는다. +- result 의 10의 자리는 스트라이크의 수를, 1의 자리는 볼의 수를 의미한다. +- createMessage() 메소드를 호출하여 result 값에 따라 알맞은 결과 메시지를 출력한다. +- 정답을 맞춘 경우 isRestart() 메소드를 호출하여 게임의 지속 여부를 결정한다. +### 5. createMessage(int result) +- result 값에 따라 알맞은 메시지를 생성하는 메소드이다. +- result가 30이라면 모두 3 스트라이크를 의미하므로 이에 따른 메시지를 리턴한다. +- 이후 result가 0이 아니라면 1의 자리 수는 ball을 의미하므로 알맞은 메시지를 리턴한다. +- 위 두 조건을 모두 충족하지 않는다면 0인 것이므로 "낫싱"을 리턴한다. +### 6. isRestart() +- 사용자의 입력값에 따라 게임의 지속 여부를 결정하는 메소드 +- 사용자의 입력이 1이라면 setAnswer() 메소드를 호출하여 answer를 변경한 뒤 true를 리턴한다. +- 사용자의 입력이 2라면 false를 리턴한다. \ No newline at end of file diff --git a/src/main/java/NumberBaseball.java b/src/main/java/NumberBaseball.java new file mode 100644 index 00000000..35401c9a --- /dev/null +++ b/src/main/java/NumberBaseball.java @@ -0,0 +1,76 @@ +import java.util.Random; +import java.util.Scanner; + +public class NumberBaseball { + public static int SIZE = 3; + public static Boolean status = true; + public static int[] answer = new int[SIZE]; + public static int[] guess = new int[SIZE]; + public static Scanner sc = new Scanner(System.in); + + public static void main(String[] args) { + + setAnswer(); + while (status) { + System.out.print("숫자를 입력해주세요 : "); + int inputNumber = sc.nextInt(); + setGuess(inputNumber); + status = checkGuess(); + } + } + + public static void setAnswer() { + while (true) { + Random random = new Random(); + answer[0] = random.nextInt(9) + 1; + answer[1] = random.nextInt(9) + 1; + answer[2] = random.nextInt(9) + 1; + if (answer[0] != answer[1] && answer[1] != answer[2] && answer[2] != answer[0]) break; + } + } + + public static void setGuess(int inputNumber) { + guess[0] = inputNumber / 100; + guess[1] = inputNumber % 100 / 10; + guess[2] = inputNumber % 10; + } + + public static boolean checkGuess() { + int result = checkSingleDigit(0) + checkSingleDigit(1) + checkSingleDigit(2); + System.out.println(createMessage(result)); + + if (result == 30) { + return isRestart(sc.nextInt()); + } + return true; + } + + public static String createMessage(int result) { + if (result == 30) { + return "3개의 숫자를 모두 맞히셨습니다! 게임 종료\n게임을 새로 시작하려면 1, 종료하려면 2를 입력하세요."; + } + if (result != 0) { + return String.format("%d 스트라이크 %d 볼", result / 10, result % 10); + } + return "낫싱"; + } + + public static int checkSingleDigit(int idx) { + if (answer[idx] == guess[idx]) { + return 10; + } + if (answer[(idx + 1) % 3] == guess[idx] || answer[(idx + 2) % 3] == guess[idx]) { + return 1; + } + return 0; + } + + public static boolean isRestart(int restart) { + if (restart == 1) { + setAnswer(); + return true; + } + return false; + } + +} diff --git a/src/test/java/NumberBaseballTest.java b/src/test/java/NumberBaseballTest.java new file mode 100644 index 00000000..ddd53a7a --- /dev/null +++ b/src/test/java/NumberBaseballTest.java @@ -0,0 +1,67 @@ +import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.BeforeAll; +import org.junit.jupiter.api.DisplayName; +import org.junit.jupiter.api.Test; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.not; + +class NumberBaseballTest { + + NumberBaseball numberBaseball = new NumberBaseball(); + static int input = 935; + @BeforeAll + static void setAnswer(){ + NumberBaseball.setAnswer(); + NumberBaseball.setGuess(input); + } + + @Test + @DisplayName("각 자리의 숫자가 서로 다른지 확인") + void setAnswer_ShouldEachAnswerDigitsAreDifferent(){ + int[] answer = NumberBaseball.answer; + + assertThat(answer[0]).isNotEqualTo(answer[1]); + assertThat(answer[1]).isNotEqualTo(answer[2]); + assertThat(answer[2]).isNotEqualTo(answer[0]); + } + + @Test + @DisplayName("input을 정상적으로 slicing 하는지 확인") + void getGuess_ShouldGenerateTheExpectedGuess() { + + int[] actual = NumberBaseball.guess; + int[] expected = new int[]{9, 3, 5}; + + assertThat(actual).isEqualTo(expected); + } + + @Test + @DisplayName("guess의 특정 digit가 올바른 볼카운트를 생성하는지 확인") + void checkSingleDigit_ShouldGenerateTheExpectedCount() { + NumberBaseball.answer = new int[]{9, 2, 3}; + + assertThat(NumberBaseball.checkSingleDigit(0)).isEqualTo(10); + assertThat(NumberBaseball.checkSingleDigit(1)).isEqualTo(1); + assertThat(NumberBaseball.checkSingleDigit(2)).isEqualTo(0); + } + + @Test + @DisplayName("알맞은 메시지 생성 여부를 확인") + void createMessage_ShouldGeneratedExpectedMessage() { + String actual1 = NumberBaseball.createMessage(30); + String actual2 = NumberBaseball.createMessage(11); + String actual3 = NumberBaseball.createMessage(0); + + assertThat(actual1).isEqualTo("3개의 숫자를 모두 맞히셨습니다! 게임 종료\n게임을 새로 시작하려면 1, 종료하려면 2를 입력하세요."); + assertThat(actual2).isEqualTo("1 스트라이크 1 볼"); + assertThat(actual3).isEqualTo("낫싱"); + } + + @Test + @DisplayName("알맞은 boolean 값을 리턴하는지 확인") + void isRestart_ShouldReturnExpectedValue() { + assertThat(NumberBaseball.isRestart(1)).isTrue(); + assertThat(NumberBaseball.isRestart(2)).isFalse(); + } +}