
动规 DP
文章平均质量分 61
GooMaple
这个作者很懒,什么都没留下…
展开
专栏收录文章
- 默认排序
- 最新发布
- 最早发布
- 最多阅读
- 最少阅读
-
UVa 10827 - Maximum sum on a torus
这道题是求最大子矩阵和的加强版,原矩阵是一个上下左右都可以串通的矩阵环,原方法是将原矩阵复制为四个,然后依次以n*n的矩阵为原型照搬最大子矩阵和的DP,但其复杂度为O(n5),交上后TLE,修改了若干变不是WA,就是TLE,最后,参考了结题报告,复制完矩阵后,枚举所求最大子矩阵在第一个矩阵中的左上角,再通过动态规划的方法求出长宽不大于N的最大子矩阵,各种枚举情况中的最大和即为所求解。 代码如下:原创 2012-08-08 17:15:11 · 1138 阅读 · 0 评论 -
UVa 147 - Dollars
完全背包,注意精度问题,我是直接把小数分成两个整数做的。 代码如下: #include #include using namespace std; long long dp[8005]; int coin[11] = {1, 2, 4, 10, 20, 40, 100, 200, 400, 1000, 2000}; int main() { int num, a, b;原创 2013-04-15 18:50:05 · 1563 阅读 · 2 评论 -
UVa 10130 - SuperSale
0-1背包,最后将每个人的最大价值都加起来,就是总的最大价值。 代码如下: #include #include #include #include using namespace std; int p[1002], w[1002], mw[102], dp[32]; int main() { #ifdef test freopen("input.txt", "r", stdin原创 2013-04-24 19:54:40 · 1081 阅读 · 0 评论 -
UVa 624 - CD
计算磁带能装下的最大音乐的时长。 0-1背包的变形,注意因为需要按从前往后的顺序打印路径,所以在分阶段DP时,需要从后往前。 代码如下: #include #include #include #include using namespace std; const int Maxn = 20; int cd[Maxn], dp[Maxn*500]; bool vis[Maxn][Max原创 2013-04-24 20:24:07 · 1062 阅读 · 0 评论 -
UVa 531 - Compromise
最长公共子序列,打印路径,注意格式的打印。 代码如下: #include #include #include #include using namespace std; char w1[100][31], w2[100][31]; int dp[101][101], path[101][101]; void Print(int sum, int i, int j)//递归打印路径 {原创 2013-04-24 21:41:36 · 1392 阅读 · 0 评论 -
UVa 10465 - Homer Simpson
可以用完全背包来做,也可以用贪心的方法来做。 贪心的话: (1)如果恰好可以凑成t,则更新最大汉堡数(即:A+B最大)。 (2)如果凑不成t,则在 t-max最小的情况下,更新A+B的最大值。 贪心法(0.024s): #include #include #include #include using namespace std; int _max; int main(原创 2013-04-26 21:21:34 · 1117 阅读 · 0 评论 -
UVa 10285 - Longest Run on a Snowboard
算最长路,最长上升子序列的变形。 代码如下: #include #include #include #include using namespace std; int dp[101][101], graph[101][101]; int n, r, c; int DP(int i, int j) { if(dp[i][j] > 0) return dp[i][j原创 2013-04-26 23:24:34 · 966 阅读 · 0 评论 -
UVa 562 - Dividing coins
题意为将硬币分成俩堆使两堆硬币的差值最小。 0-1背包,可以将硬币能凑成的所有和都计算出来,然后从sum/2(sum为所有硬币的和)开始向0探寻,直到找到所给硬币能凑成的最大的硬币和 i,然后其最小差便为sum-2*i。 代码如下: #include #include #include #include using namespace std; const int Maxn = 10原创 2013-04-18 19:59:03 · 1635 阅读 · 0 评论 -
UVa 10069 - Distinct Subsequences
dp+大数加法。 设母串的长度为 j, 子串的长度为 i,我们要求的就是长度为 i 的字串在长度为 j 的母串中出现的次数。 (1)若母串的最后一个字符与子串的最后一个字符不同,则长度为 i 的子串在长度为 j 的母串中出现的次数就是母串的前 j - 1 个字符中子串出现的次数,即 str[i][j] = str[i][j - 1]; (2)若母串的最后一个字符与子串的最后一个字符相同,那么原创 2013-05-02 20:48:47 · 1569 阅读 · 0 评论 -
UVa 10154 - Weights and Measures
先按力量排序,然后dp在前i个乌龟中j个乌龟可以重叠的最小重量,其实就是对于每个乌龟i选或是不选的问题。状态方程:dp[i, j] = min{dp[i, j-1], dp[i-1, j-1]+w[i]}. 代码如下: #include #include #include #include using namespace std; typedef struct Turtle {原创 2013-05-02 23:36:56 · 1023 阅读 · 0 评论 -
UVa 10404 - Bachet's Game
类似巴什博奕,先行者要赢,假设先行者必赢的状态为1,必输为0。 则其通过集合中存在的数可以达到之前的某个0的状态,则当前状态为1,如果通过所有集合中的数都无法达到之前的某个为0的状态(即:可到达的之前状态全为1),则当前状态为0。 因为先行者如果可以达到之前某个为0的状态,则说明其达到前面这个0的状态时它实际对于之前的这个状态来说是个后行者,0代表在之前的这个状态来说是后行者赢,则对现在状态来原创 2013-05-03 22:39:28 · 903 阅读 · 0 评论 -
UVa 357 - Let Me Count The Ways
完全背包问题。 代码如下: #include #include using namespace std; long long dp[30055]; int coin[5] = {1, 5, 10, 25, 50}; int main() { int num; dp[0] = 1; for(int i=0; i<5; ++i) { for(in原创 2013-04-15 19:53:07 · 1467 阅读 · 0 评论 -
UVa 674 - Coin Change
第一个动归程序,完全背包,本来是用记忆化搜索做的(貌似需要开二维数组来标记,一维数组标记不完,总有重复的数据),没做出来,用递推写了一下,过了~ 代码如下: #include #include using namespace std; int dp[8000]; int coin[5] = {1, 5, 10, 25, 50}; int main() { dp[0] = 1;原创 2013-03-25 21:53:58 · 765 阅读 · 0 评论 -
UVa 507 - Jill Rides Again
最大连续和问题,注意其还有一要求是需要路径最长,即:当其和相同时,取路程最大的一段路的起点和终点,也就是说如果其和相同但其路径较短则不必更新先前保存的起点与终点位置。 代码如下: #include #include #include #include #include #include using namespace std; int main() { #ifdef test原创 2012-08-07 17:13:06 · 742 阅读 · 0 评论 -
UVa 108 - Maximum Sum
求矩阵的最大子矩阵。 代码如下: 方法一(普通方法效率较低,跑了1秒多): #include #include using namespace std; int a[110][110] = {{0}}; int main() { int n, i, j, k, tmp, sum; while (scanf("%d", &n) == 1) { f原创 2012-08-08 12:19:49 · 1072 阅读 · 0 评论 -
UVa 10003 - Cutting Sticks
状态方程:dp[i,j] = min(dp[i,k], dp[k,j])+j-i,记忆化搜索。 代码如下: #include #include #include const int MAXN = 52; int stick[MAXN], n; int dp[MAXN][MAXN]; int DP(int l, int r) { if(dp[l][r] != -1) {原创 2013-04-01 20:37:19 · 898 阅读 · 0 评论 -
UVa 116 - Unidirectional TSP
状态方程:max{ dp[i+1,j+1], dp[i,j+1], dp[i-1,j+1]},路径打印也是利用动归的思想,每个状态下在保证路径权值最小的情况下保证起始行数为较小值。 代码如下: #include #include #include using namespace std; #define inf 0x7FFFFFFF const int MAXN = 12; cons原创 2013-04-09 21:33:17 · 2028 阅读 · 0 评论 -
UVa 103 - Stacking Boxes
最长上升子序列,用记忆化搜索做的,比较慢。 代码如下: #include #include #include int num, ver, cct; int dp[32], path[30][30]; int save[30], box[30][10]; bool G[31][31]; int cmp(const void *a, const void *b) { return原创 2013-03-27 21:11:29 · 749 阅读 · 0 评论 -
UVa 10405 - Longest Common Subsequence
最长公共子序列。 代码如下: #include #include int dp[1002][1002]; int iMax(int a, int b) { if(a > b) return a; return b; } int main() { char str1[1002], str2[1002]; while(gets(str原创 2013-03-27 18:27:43 · 735 阅读 · 0 评论 -
UVa 10066 - The Twin Towers
实际上就是一个纯的最长公共子序列。 代码如下: #include #include #include using namespace std; int main() { #ifdef test freopen("input.txt", "r", stdin); #endif int n1, n2, cct = 0; int tower_1[102], tower_原创 2013-04-10 19:42:53 · 939 阅读 · 0 评论 -
UVa 111 - History Grading
最长公共子序列,不过输入序列的方式有些特殊。 代码如下: #include #include int dp[22][22], ans[22], stu[22]; int iMax(int a, int b) { if(a > b) return a; return b; } int main() { int num, t; scanf("%原创 2013-03-27 19:23:14 · 997 阅读 · 0 评论 -
UVa 10131 - Is Bigger Smarter?
最长上升子序列,不过需要略微处理一下,先按重量从小到大排一下序,然后找IQ的最长下降子序列。 代码如下: #include #include #include #include using namespace std; struct elephant { int wei, iq, num; } ele[1002]; int cct, dp[1002]; int cmp(cons原创 2013-04-11 20:00:03 · 778 阅读 · 0 评论 -
UVa 10192 - Vacation
最长公共子序列。 代码如下: #include #include #include #include using namespace std; #define Maxn 102 int main() { #ifdef test freopen("input.txt", "r", stdin); #endif int dp[Maxn][Maxn]; int len原创 2013-04-11 20:19:51 · 767 阅读 · 0 评论 -
UVa 437 - The Tower of Babylon
最长公共子序列,将1改为相应权值(即:每个长方体的高度值),其中注意给出的n个长方体,是长方体的种数,也就是说每种长方体可以有无数个。 代码如下: #include #include #include #include using namespace std; int step[3][3]={{0,1,2}, {0,2,1}, {1,2,0}}; int num, dp[100], t原创 2013-05-03 22:02:38 · 1200 阅读 · 0 评论