티스토리 뷰
문제
문제 링크: https://www.acmicpc.net/problem/14501
문제를 보면 DP로 풀 수 있다는 것을 알 수 있습니다.
검색을 해본 결과 DFS로도 풀 수 있다는 것을 알게되었습니다.
문제를 풀때 꼭 한 방법만이 아닌 다른 방법도 생각하는 습관을 들이는 것이 좋을것 같습니다.ㅎㅎ;;
이 문제는 상담을 하거나 안하거나 둘중 하나를 고르는 것이 관건인 문제입니다.
DP의 경우는 점화식을 세워서 문제를 풀며, 점화식은 max(dp(day+1), dp(day+T[day])+P[day]) 입니다.
전자 의 경우는 상담을 안 하였을때의 식이며, 후자의 경우는 상담을 하였을 때의 식입니다.
T[day]는 해당 날짜의 상담을 했을 경우 걸리는 시간이며, P[day]는 그에 따른 보수입니다.
DFS 경우에도 DP와 똑같은 식을 사용하여 풀었습니다.
모든 경우의 수를 다 해보아도 퇴사날의 크기가 작기 때문에 시간상으로도 문제가 되지 않습니다.
코드
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 | #include <iostream> #include <algorithm> using namespace std; int D[16]; int T[16]; int P[16]; int n; int ans; //dp의 경우 int dp(int day){ if(day == n+1) return 0; //날짜가 n+1보다 크다면 -값을 크게 준다. if(day > n+1) return -987654321; //메모이제이션 if(D[day] > 0) return D[day]; //점화식 상담을 안한다 혹은 상담을 한다. 둘 중 하나를 고른다. return D[day] = max(dp(day+1), dp(day+T[day])+P[day]); } //dfs의 경우(모든 경우를 해본다.) void dfs(int day, int sum){ if(day == n+1){ ans = max(ans, sum); return; } //상담을 안하는 경우 dfs(day+1, sum); //상담을 할 수 있을 경우는 상담을 한다. if(day+T[day] <= n+1) dfs(day+T[day], sum+P[day]); } int main(){ cin >> n; for(int i = 1; i <= n; i++) cin >> T[i] >> P[i]; cout << dp(1)<<"\n"; dfs(1,0); cout << ans <<"\n"; return 0; } | cs |
'알고리즘 문제 풀이 > BOJ' 카테고리의 다른 글
백준 14503: 로봇 청소기 (0) | 2018.01.19 |
---|---|
백준 14500: 테트로미노 (0) | 2018.01.19 |
백준 14502: 연구소 (6) | 2018.01.18 |
백준 2667: 단지번호 붙이기, 4963: 섬의 개수 (0) | 2018.01.13 |
백준 1707: 이분 그래프 (0) | 2018.01.10 |