
https://www.acmicpc.net/problem/2503
import java.util.*;
import java.io.*;
class Main {
public static void main(String[] args) throws Exception {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
int N = Integer.parseInt(br.readLine());
List<Query> querys = new ArrayList<>();
for (int i = 0; i < N; i++) {
StringTokenizer st = new StringTokenizer(br.readLine());
int answer = Integer.parseInt(st.nextToken());
int strike = Integer.parseInt(st.nextToken());
int ball = Integer.parseInt(st.nextToken());
querys.add(new Query(answer, strike, ball));
}
int result = 0;
for (int num = 123; num < 988; num++) {
if (!isValid(num)) {
continue;
}
int correctCount = 0;
for (Query query : querys) {
int strikeCount = 0;
int ballCount = 0;
String numStr = Integer.toString(query.answer);
String targetStr = Integer.toString(num);
// 스트라이크 검사
for (int i = 0; i < 3; i++) {
if (numStr.charAt(i) == targetStr.charAt(i)) {
strikeCount++;
}
}
if (strikeCount != query.strike) {
break;
}
// 볼 검사
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 3; j++) {
if (numStr.charAt(i) == targetStr.charAt(j) && (i != j)) {
ballCount++;
}
}
}
if (ballCount != query.ball) {
break;
}
if (strikeCount == query.strike && ballCount == query.ball) {
correctCount++;
}
}
if (correctCount == N) {
result++;
}
}
System.out.println(result);
}
static boolean isValid(int num) {
int first = num / 100;
int second = num % 100 / 10;
int third = num % 10;
if (second == 0 || third == 0) {
return false;
}
if (first == second || second == third || first == third) {
return false;
}
return true;
}
static class Query {
int answer;
int strike;
int ball;
Query(int answer, int strike, int ball) {
this.answer = answer;
this.strike = strike;
this.ball = ball;
}
}
}
스트라이크 또는 볼의 개수로 상대방이 생각한 수를 유추하는 것이 목적이라면, 이 문제는 특이하게 상대방이 생각할 가능성이 있는 수의 개수를 구하는 것이었다.물어본 숫자, 스트라이크의 개수, 볼의 개수가 순차적으로 한 줄에 주어진다.
123, 1, 2라는 입력이 주어졌을 때 123이라는 숫자에 대해서 스트라이크 1개와 볼 2개가 될 수 있는 모든 숫자를 의미한다.Query라는 객체 리스트에 저장한다. 그 후 123 ~ 987에 존재하는 숫자들에 대해서 query를 모두 만족하는 수들을 구한다.1) 서로 겹치면 안되며(ex 112) 2) 0이 들어가면 안된다. (120)123, 1, 2라는 입력에 대해서 132 라는 값은 1스트라이트 2볼이라는 조건에 부합한다.strike의 경우는 num.charAt(i)과 target.charAt(i)가 만족하는 경우를 의미한다.ball의 경우는 수가 안에 존재하지만, 자리는 다른 경우를 의미한다. 따라서 이중for문을 사용하며 num.charAt(i) == target.charAt(j)이면서 i != j인 경우가를 의미한다.result를 1증가시킨다.브루트포스로도 충분히 선형의 시간복잡도로 해결할 수 있다.