숫자 야구 프로그램

박영준·2023년 6월 13일
0

Java

목록 보기
80/112

1. 조건

2. 출력 결과 예시

방법

로직의 흐름을 구상해보자면,

  • 컴퓨터

    • 랜덤 숫자 뽑기
  • 사용자

    • 랜덤 숫자 입력
    • 입력 결과 판단
    • 종료 or 재시작

방법 1 : 배열 + Scanner

Main 클래스에 구현했다.

import java.util.Random;
import java.util.Scanner;

public class Main {
    public static void main(String[] args) {

        Random random = new Random();
        Scanner sc = new Scanner(System.in);

        int[] comArr = new int[3];         // 컴퓨터가 뽑은 랜덤 숫자 배열 생성

        // 랜덤 숫자 담기
        for (int i = 0; i < comArr.length; i++) {
            comArr[i] = random.nextInt(9);      // 한 자리씩 랜덤 숫자 담기
            // 숫자 중복 확인
            for (int j = 0; j < i; j++) {
                // 중복되면, 전 단계로 이동
                if (comArr[i] == comArr[j]) {
                    i--;
                    break;
                }
            }
        }
        System.out.println("컴퓨터가 숫자를 생성하였습니다. 답을 맞춰보세요!");

        int tryCnt = 0;     // 시도 횟수

        // 사용자가 숫자 맞추기
        while(true) {
            tryCnt++;

            System.out.print(tryCnt + "번째 시도 : ");
            String inputNum = sc.nextLine();        // 숫자 입력 (string)

            int[] userArr = new int[3];             // 사용자가 입력한 숫자 배열 생성

            // 사용자가 입력한 문자열 -> userArr 정수 배열로 변환
            for (int i = 0; i < inputNum.length(); i++) {
                userArr[i] = Character.getNumericValue(inputNum.charAt(i));        // 문자열 -> 문자(char) -> 정수(int) 로 배열에 담기
            }

            int strike = 0;
            int ball = 0;

            for (int i = 0; i < userArr.length; i++) {
                // 스트라이크 일 경우 (숫자 값, 위치 일치)
                if (userArr[i] == comArr[i]) {
                    strike++;

                    // 볼 일 경우 (숫자 값 일치, 위치 다름)
                } else {
                    for (int j = 0; j < userArr.length; j++) {
                        if (userArr[i] == comArr[j]) {
                            ball++;
                        }
                    }
                }
            }

            // 스트라이크만 모두 나온 경우(세 자리 모두 맞혔을 경우) -> 종료
            if (strike == 3) {
                System.out.println(strike + "S");
                System.out.println(tryCnt + "번만에 맞히셨습니다.");
                break;
            // 볼만 모두 나온 경우 -> 다시 반복문으로
            } else if (ball == 3) {
                System.out.println(ball + "B");
            //  모두 맞히지 못한 경우 -> 다시 반복문으로
            } else {
                System.out.println(strike + "S" + ball + "B");
            }
        }

        System.out.println("게임을 종료합니다.");
    }
}
  • random.nextInt(9) 으로 0 ~ 9 사이의 값을 랜덤하게 담는다.

    • random.nextInt(max) + min 이므로, random.nextInt(9) + 0 이라고 간주하면 된다.
      • max : 랜덤 값 중 가장 큰 값
      • min : 랜덤값 중 가장 작은 값
  • Character.getNumericValue()

    • 숫자로 된 문자(char) -> int 형 변환

방법 2 : 클래스 나누기

Main 클래스

public class Main {
    static MakeRandom makeRandom = new MakeRandom();        // 랜덤값 3개
    static PrintResult printResult = new PrintResult();     // 결과 출력
    static BallAndStrikeCheck ballAndStrikeCheck = new BallAndStrikeCheck();        // Ball, Strike 구분

    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));       // BufferedReader 사용 : scanner 와 System.out.println()에 비해 훨씬 빠르기 때문에 多 데이터 처리 시 유리 (단, 데이터는 String 으로 고정)
        System.out.println("컴퓨터가 숫자를 생성하였습니다. 답을 맞춰보세요!");

        ArrayList computerNumbers = (ArrayList) makeRandom.makeRandomNumber();      // ArrayList 사용
        int cnt = 0;

        while (true) {
            cnt++;
            System.out.print(cnt + "번째 시도: ");
            String input = br.readLine();

            String[] userInput = input.split("");
            ArrayList userNumbers = new ArrayList(List.of(userInput));

            int[] result = ballAndStrikeCheck.ScoreCheck(computerNumbers, userNumbers);
            printResult.print_result(cnt, result);

            if (result[1] == 3) {
                break;
            }
        }
    }
}
  • 각 기능별로 클래스를 만들고, 해당 객체를 불러와 인스턴스화을 통해 참조하도록 했다.

BallAndStrikeCheck 클래스

public class BallAndStrikeCheck {
    static int[] score = new int[2];        // 길이 2의 배열 생성
    public int[] ScoreCheck(List userInput, List randomNumber) {
        score[0] = 0;
        score[1] = 0;

        // 각 배열에 숫자 입력
        for (int i = 0; i < 3; i++) {
            if (userInput.get(i).equals(randomNumber.get(i))) {
                score[1] += 1;
            } else if (randomNumber.contains(userInput.get(i))) {
                score[0] += 1;
            }
        }

        return score;
    }
}

PrintResult 클래스

public class PrintResult {
    static void print_result(int cnt, int[] result_cnt) {

        // [ball, strike]

        // 3S 일 경우
        if (result_cnt[1] == 3) {
            System.out.println(result_cnt[1] + "S");
            System.out.println(cnt+"번째만에 맞추셨습니다!");
            System.out.println("게임을 종료합니다.");

        // 3B 일 경우
        } else if (result_cnt[0] == 3) {
            System.out.println(result_cnt[0] + "B");

        // S 와 B 이 섞인 경우
        } else {
            System.out.println(result_cnt[0] + "B" + result_cnt[1] + "S");
        }
    }
}

MakeRandom 클래스

public class MakeRandom {
    LinkedHashSet<String> randomNumber = new LinkedHashSet<>();     // LinkedHashSet 사용 : 중복 X, 저장순서 유지 O

    public List<String> makeRandomNumber() {
        
        // 랜덤 숫자 길이를 3으로 만든다
        while (randomNumber.size() != 3) {
            randomNumber.add(String.valueOf((int)(Math.random() * 9)));
        }

        List<String> baseBallList = new ArrayList<>(randomNumber);      // ArrayList 선언 & randomNumber 값 추가
        return baseBallList;
    }
}
profile
개발자로 거듭나기!

0개의 댓글