https://www.acmicpc.net/problem/2961

 

2961번: 도영이가 만든 맛있는 음식

첫째 줄에 재료의 개수 N(1 ≤ N ≤ 10)이 주어진다. 다음 N개 줄에는 그 재료의 신맛과 쓴맛이 공백으로 구분되어 주어진다. 모든 재료를 사용해서 요리를 만들었을 때, 그 요리의 신맛과 쓴맛은

www.acmicpc.net

코드설명

일반적인 완전탐색 문제로, DFS를 통하여 만들 수 있는 음식의 조합을 구한다음에 신맛과 쓴맛의 차이점을 구하면 됩니다.

 

처음에 계속해서 틀려서 어떤이유인지 확인결과 level > 1 초과로 코딩을 해놓아서 올바르게 나오지 않았습니다.

if( level >= 1) {
result = Math.min(result, Math.abs(sourTaste - hurtTaste));
}

또 처음에 제가 작성한 코드처럼 조합을 구해서 진행하는방식이 아닌 다른방식도 같이 작성해보았습니다.

 

 

코드

조합을 통해 결과를 구함

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.*;
public class Main {
public static String T;
public static int N;
public static Node[] Node;
public static boolean[] visited;
public static long result = Integer.MAX_VALUE;
public static void main(String[] args) throws IOException{
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine());
N = Integer.parseInt(st.nextToken());
Node = new Node[N];
visited = new boolean[N];
for(int i=0;i<N;i++) {
st = new StringTokenizer(br.readLine());
int a = Integer.parseInt(st.nextToken());
int b = Integer.parseInt(st.nextToken());
Node[i] = new Node(a, b);
}
simulate(0, 1, 0, 0);
System.out.println(result);
}
public static void simulate(int idx, long sourTaste, int hurtTaste, int level) {
if(level == N) {
result = Math.min(result, Math.abs(sourTaste - hurtTaste));
return ;
}
if( level >= 1) {
result = Math.min(result, Math.abs(sourTaste - hurtTaste));
}
for(int i=idx;i<N;i++) {
if(visited[i] == true) continue;
Node temp = Node[i];
int sourTasteTemp = temp.sourTaste;
int hurtTasteTemp = temp.hurtTaste;
visited[i] = true;
simulate(i + 1, sourTaste * sourTasteTemp , hurtTaste + hurtTasteTemp, level + 1);
visited[i] = false;
}
}
}
class Node{
int sourTaste; //신맛
int hurtTaste; //쓴맛
public Node(int sourTaste, int hurtTaste) {
this.sourTaste = sourTaste;
this.hurtTaste = hurtTaste;
}
}

 

 

DFS 분기처리를 통해 구함( 조합을 구한것과 마찬가지자만 방향이 살짝 다르다. )

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.*;
public class Main {
public static String T;
public static int N;
public static Node[] Node;
public static boolean[] visited;
public static long result = Integer.MAX_VALUE;
public static void main(String[] args) throws IOException{
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine());
N = Integer.parseInt(st.nextToken());
Node = new Node[N];
visited = new boolean[N];
for(int i=0;i<N;i++) {
st = new StringTokenizer(br.readLine());
int a = Integer.parseInt(st.nextToken());
int b = Integer.parseInt(st.nextToken());
Node[i] = new Node(a, b);
}
simulate(0);
System.out.println(result);
}
public static void simulate(int level) {
if(level == N) {
int sour = 1;
int hurt = 0;
for(int i=0;i<N;i++) {
if(visited[i] == true) {
sour *= Node[i].sourTaste;
hurt += Node[i].hurtTaste;
}
}
if(sour!= 1 && hurt != 0) result = Math.min(result, Math.abs(sour - hurt));
return ;
}
visited[level] = true;
simulate(level + 1);
visited[level] = false;
simulate(level + 1);
}
}
class Node{
int sourTaste; //신맛
int hurtTaste; //쓴맛
public Node(int sourTaste, int hurtTaste) {
this.sourTaste = sourTaste;
this.hurtTaste = hurtTaste;
}
}

 

 

정답코드3입니다. 가장 짧은 코드

package Main;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.StringTokenizer;
public class Main {
public static int C, N, H, W, K, M;
public static int answer = 0;
public static int[][] food;
public static void main(String[] args) throws IOException{
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine());
N = Integer.parseInt(st.nextToken());
food = new int[N][2];
for(int i=0;i<N; i++) {
st = new StringTokenizer(br.readLine());
int a = Integer.parseInt(st.nextToken());
int b = Integer.parseInt(st.nextToken());
food[i][0] = a;
food[i][1] = b;
}
System.out.println(bruteforce(0, 0, 0));
}
public static long bruteforce(int depth, int now, int visited) {
if(depth == N) {
return calculate(visited);
}
long ret = Long.MAX_VALUE;
ret = bruteforce(depth + 1, now + 1, visited + (1 << now));
ret = Math.min(ret, bruteforce(depth + 1, now + 1, visited));
return ret;
}
public static long calculate(int visited) {
boolean isContainsZeroFood = true;
long aTaste = 1, bTaste = 0;
for(int i=0; i<N; i++) {
if( (visited & (1<<i)) > 0) {
isContainsZeroFood = false;
aTaste *= food[i][0];
bTaste += food[i][1];
}
}
if(isContainsZeroFood) return Long.MAX_VALUE;
return Math.abs(aTaste - bTaste);
}
}

+ Recent posts