차곡차곡

[BOJ/Python, Java] 백준 2503번 - 숫자 야구 본문

CS/Algorithm

[BOJ/Python, Java] 백준 2503번 - 숫자 야구

sohy 2023. 8. 2. 17:32

백준 #2503 숫자 야구

 

2503번: 숫자 야구

첫째 줄에는 민혁이가 영수에게 몇 번이나 질문을 했는지를 나타내는 1 이상 100 이하의 자연수 N이 주어진다. 이어지는 N개의 줄에는 각 줄마다 민혁이가 질문한 세 자리 수와 영수가 답한 스트

www.acmicpc.net

 

Python ver.

# 서로 다른 숫자(1~9 중)로 만들 수 있는 모든 세 자리 수
def makeNums(idx):  
    if idx == 3:
        possible.append("".join(nums))
        return
    for i in range(1, 10):
        if is_selected[i]: continue
        is_selected[i] = True
        nums[idx] = str(i)
        makeNums(idx+1)
        is_selected[i] = False


# 번호와 정보가 일치하는지 검사
def guess(num, guess_num, s, b):
    guess_s, guess_b = 0, 0
    for i in range(3):
        for j in range(3):
            if num[i] == guess_num[j]:
                if i == j:
                    guess_s += 1
                else:
                    guess_b += 1
    if guess_s == s and guess_b == b:
        return True
    else:
        return False



n = int(input())
info = [list(map(int, input().split())) for _ in range(n)]  # [질문한 세 자리 수, 스트라이크 개수, 볼 개수]
possible = []
is_selected = [False] * 10  # 사용된 숫잔지 확인
nums = [0] * 3
cnt = 0

makeNums(0)

for guess_num in possible:
    flag = True
    for num, s, b in info:
        if not guess(str(num), guess_num, s, b):
            flag = False
            break
    if flag:
        cnt +=1

print(cnt)

 

Java ver.

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.StringTokenizer;

public class Main {
	
	static int n, cnt;
	static String[] nums;
	static int[] strike, ball, guessNum;
	static ArrayList<int[]> possible;
	static boolean[] isSelected;
	
	// 서로 다른 숫자(1~9 중)로 만들 수 있는 모든 세 자리 수
	public static void makeNums(int idx) {
		if (idx == 3) {
			possible.add(Arrays.copyOf(guessNum, 3));
			return;
		}
		for (int i = 1; i < 10; i++) {
			if(isSelected[i]) continue;
			isSelected[i] = true;
			guessNum[idx] = i;
			makeNums(idx+1);
			isSelected[i] = false;
		}
	}
	
	// 번호와 정보가 일치하는지 검사 (검사할 질문한 수, 후보 수, 스트라이크 개수, 볼 개수)
	public static boolean guess(String num, int[] gn, int s, int b) {
		int guessS = 0;
		int guessB = 0;
		for (int i = 0; i < 3; i++) {
			for (int j = 0; j < 3; j++) {
				int n = num.charAt(i) - '0';
				if (n == gn[j]) {
					if (i == j) guessS++;
					else guessB++;
				}
			}
		}
		if (guessS == s && guessB == b) return true;
		else return false;
	}
	
	public static void main(String[] args) throws IOException {
		BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
		
		// 입력
		int n = Integer.parseInt(br.readLine());  // 질문 개수
		nums = new String[n];  // 질문한 수
		strike = new int[n];  // 스트라이크 개수
		ball = new int[n];  // 볼 개수
		possible = new ArrayList<int[]>();  // 모든 세 자리 수 후보
		isSelected = new boolean[10];  // 사용된 숫잔지 확인
		guessNum = new int[3];

		for (int i = 0; i < n; i++) {
			StringTokenizer st = new StringTokenizer(br.readLine());
			nums[i] = st.nextToken();
			strike[i] = Integer.parseInt(st.nextToken());
			ball[i] = Integer.parseInt(st.nextToken());
			
		}
		
		makeNums(0);  // 가능한 모든 수 생성
		for (int i = 0; i < possible.size(); i++) {
			boolean flag = true;
			for (int j = 0; j < n; j++) {
				if(!guess(nums[j], possible.get(i), strike[j], ball[j])) {
					flag = false;
					break;
				}
			}
			if (flag) cnt++;
		}
		
		System.out.println(cnt);
	
		
	}

}
  1. 가능한 1에서 9까지의 서로 다른 숫자 세 개로 구성된 세 자리 수를 모두 구한다.
  2. 질문으로 들어온 숫자와 비교하여 스트라이크, 볼 개수를 구한다.
  3. 질문으로 들어온 모든 숫자에 대해 스트라이크, 볼 개수가 일치하면 가능성 있는 답으로 개수를 +1 해준다.
  4. 하나라도 스트라이크, 볼 개수가 일치하지 않으면 가능성 없는 답
Comments