실버 3
https://www.acmicpc.net/problem/18429
백트래킹 사용
1) 틀린 코드 풀이
ex) n=3, k=4, 운동키트번호(중량증가량) 1(3),2(7),3(5)
1. 키트를 사용할 수 있는 경우의 수를 구하기 위해 백트래킹을 수행
1,2,3
1,3,2
2,1,3
2,3,1
3,1,2
3,2,1
총 6가지 방법을 키트를 사용할 수 있음
이러한 방법으로 문제를 해결하였는데 정답을 제출하니 25%에서 틀렸습니다가 발생했다. 일일이 모든 경우의 수를 구하고 그 중 맞는 경우를 찾아야하다보니 비효율적인 코드라는 생각이 들었다.
그래서 백트래킹을 수행하며 sum을 구하는 방법으로 수정했다.
2) 정답 풀이
static void back(int sum, int idx) {
if (idx == n) {
ans++;
return;
}
for (int i = 0; i < n; i++) {
if (!visit[i] && (sum + arr[i] - k) >= 500) {
visit[i] = true;
back(sum + arr[i] - k, idx + 1);
visit[i] = false;
}
}
}
1) 틀린 코드(25%에서 틀렸습니다)
package 백트래킹;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.StringTokenizer;
public class BOJ18429 {
static int n, k;
static int[] arr;
static boolean[] visit;
static int ans;
static int[] tmp;
static int sum;
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st;
st = new StringTokenizer(br.readLine(), " ");
n = Integer.parseInt(st.nextToken());
k = Integer.parseInt(st.nextToken());
st = new StringTokenizer(br.readLine(), " ");
arr = new int[n];
for (int i = 0; i < n; i++) {
arr[i] = Integer.parseInt(st.nextToken());
}
visit = new boolean[n];
tmp = new int[n];
ans = 0;
sum = 500;
back(0);
System.out.println(ans);
}
static void back(int idx) {
if (idx == n) {
if (checkStatus(tmp)) {
ans++;
}
return;
}
for (int i = 0; i < n; i++) {
if (!visit[i]) {
visit[i] = true;
tmp[idx] = arr[i];
back(idx + 1);
visit[i] = false;
}
}
}
static boolean checkStatus(int[] tmp) { // 계속 500이상을 유지한다면
for (int val : tmp) {
sum += val - k;
if (sum < 500) {
return false;
}
}
return true;
}
}
2) 정답코드
package 백트래킹;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.StringTokenizer;
public class BOJ18429 {
static int n, k;
static int[] arr;
static boolean[] visit;
static int ans;
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st;
st = new StringTokenizer(br.readLine(), " ");
n = Integer.parseInt(st.nextToken());
k = Integer.parseInt(st.nextToken());
st = new StringTokenizer(br.readLine(), " ");
arr = new int[n];
for (int i = 0; i < n; i++) {
arr[i] = Integer.parseInt(st.nextToken());
}
visit = new boolean[n];
ans = 0;
back(500, 0);
System.out.println(ans);
}
static void back(int sum, int idx) {
if (idx == n) {
ans++;
return;
}
for (int i = 0; i < n; i++) {
if (!visit[i] && (sum + arr[i] - k) >= 500) {
visit[i] = true;
back(sum + arr[i] - k, idx + 1);
visit[i] = false;
}
}
}
}