Notice
Recent Posts
Recent Comments
Link
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
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 |
Tags
- Bellman-Ford
- 2-sat
- topologicalsort
- mergesorttree
- LCA
- DP
- MST
- FenwickTree
- LIS
- BinarySearch
- Bridge
- greedy
- backtracking
- IndexedTree
- Math
- Implementation
- TwoPointers
- BFS
- ShortestPath
- Dijkstra
- DFS
- ArticulationPoint
- SlidingWindow
- Floyd
- KMP
- Tree
- Flow
- scc
- Union-Find
- Sweeping
Archives
- Today
- Total
정리충의 정리노트
[백준] 2624: 동전 바꿔주기 본문
0. 문제 주소
https://www.acmicpc.net/problem/2624
1. 풀이
개수의 제한에 주의할 필요가 있다.
[PS/DP] - [BOJ] 9084: 동전에서는 단순히 이번 동전을 쓰냐 / 쓰지 않느냐 로 나누어 생각한 후,
메모이제이션을 통해 테이블들을 갱신해 나갔다.
하지만 개수의 제한이 있으므로, 이번 동전을 1개 썼을 때, 2개 썼을 때, ... 최대로 썼을 때의 경우를 모두 생각해야 한다.
그러므로 dp 테이블을 2차원으로 설계한 뒤,
dp[i][j] = i번째 동전까지 써서 j원을 만들 수 있는 경우의 수 로 저장을 하면 된다.
이를 구하기 위해서는, i번째 동전의 금액을 p_i, 개수 제한을 n_i라고 했을 때,
dp[i][j] = sum (k=1 to n_i) { dp[i-1][ j - k * p_i ] } 로 계산하면 된다.
2. 풀이 코드
* 유의할 점
#include <bits/stdc++.h>
#define MAX 10005
#define pii pair<int, int>
using namespace std;
int T, K;
pii coins[105];
int dp[105][MAX];
int main(){
#ifndef ONLINE_JUDGE
freopen("input.txt", "r", stdin);
#endif // ONLINE_JUDGE
scanf("%d %d", &T, &K);
for (int i=1;i<=K;i++){
int p, n;
scanf("%d %d", &p, &n);
coins[i] = pii(p, n);
}
sort(coins+1, coins+K+1);
for (int i=0;i<=K;i++){
dp[i][0] = 1;
}
for (int i=1;i<=K;i++){
int curr_coin = coins[i].first, curr_cnt = coins[i].second;
for (int j=1;j<=T;j++){
if (j < curr_coin){
dp[i][j] = dp[i-1][j];
continue;
}
for (int k=0;k<=curr_cnt;k++){
if (j - k * curr_coin < 0) continue;
dp[i][j] += dp[i-1][j - k * curr_coin];
}
}
}
printf("%d\n", dp[K][T]);
}
'PS > DP' 카테고리의 다른 글
[백준] 10714: 케이크 자르기 2 (0) | 2020.02.29 |
---|---|
[백준] 1103: 게임 (1) | 2020.02.03 |
[백준] 1256: 사전 (0) | 2020.01.28 |
[백준] 2352: 반도체 설계 (0) | 2020.01.27 |
[백준] 2533: 사회망 서비스 (0) | 2020.01.24 |
Comments