ACM集训day15——DP

来源:互联网 发布:js isnan函数 编辑:程序博客网 时间:2024/06/05 03:34

7.25

01背包引入讲了动态规划DP

首先会有个疑问:贪心思想不能做吗?确实不能。01背包放东西只有放或不放,没有像贪心题那样可以放几分之几。而且,举个例子:3个物品大小分别是3,3,7,价值分别是6,6,10,如果背包大小是10,按贪心来做 价值/大小 降序就取得最大价值是6+6,然而明显是取6+10价值更高

经典例题:01背包

hdu2602

这里写图片描述
这里写图片描述

#include<stdio.h>#include<math.h>#include<stdlib.h>#include<iostream>#include<algorithm>#include<string.h>#include<malloc.h>#include<vector>#include<queue>#include<stack>using namespace std;int val[1005];int vol[1005];int dp[1005][1005];   /*表示前i件物品放到容量为j的背包的最大价值。如果放到主函数里面运行会崩溃,**数组开到超过6个零就放出去**,尽量大数都放出去*/int main(){    int t;    scanf("%d",&t);    while(t--)    {        memset(dp,0,sizeof(dp));        int n,v;        scanf("%d%d",&n,&v);        for(int i=1;i<=n;i++)  //从1开始,前i件嘛            scanf("%d",&val[i]);        for(int i=1;i<=n;i++)  //从1开始            scanf("%d",&vol[i]);        for(int i=1;i<=n;i++)            for(int j=0;j<=v;j++)   /*二层从0开始,要和后面dp[i][j-vol[i]]+val[i](j=vol[i])的情况比较*/        {            if(j>=vol[i])                dp[i][j]=max(dp[i-1][j],dp[i-1][j-vol[i]]+val[i]);            else dp[i][j]=dp[i-1][j];        }        printf("%d\n",dp[n][v]);    }    return 0;}

优化一下空间复杂度,用一维数组dp[]

#include<stdio.h>#include<math.h>#include<stdlib.h>#include<iostream>#include<algorithm>#include<string.h>#include<malloc.h>#include<vector>#include<queue>#include<stack>using namespace std;int val[1005];int vol[1005];           /*表示前i件物品放到容量为j的背包的最大价值。如果放到主函数里面运行会崩溃,**数组开到超过6个零就放出去**,尽量大数都放出去*/int main(){    int t;    scanf("%d",&t);    while(t--)    {        int n,v;        scanf("%d%d",&n,&v);        int dp[1005];        for(int i=0;i<=v;i++)            dp[i]=0;        for(int i=1;i<=n;i++)  //从1开始            scanf("%d",&val[i]);        for(int i=1;i<=n;i++)  //从1开始            scanf("%d",&vol[i]);        for(int i=1;i<=n;i++)            for(int j=v;j>=0;j--)   /*要从v开始倒过来,才能保证推f[v]时f[v-c[i]]保存的是状态f[i-1][v-c[i]]的值(取前i-1物品最优状态,打个表清晰明了),详见《背包九讲》博文()*/        {            if(j>=vol[i])                dp[j]=max(dp[j],dp[j-vol[i]]+val[i]);/*与二维的转移方程同价*/        }        printf("%d\n",dp[v]);    }    return 0;}

这里写图片描述
优化后,同是C++,时间和内存都优化了不少,G++更优一些

下午机房空调崩了….
dp代码都不难写,但有时候很难想得通,思想很重要,这才是刚刚开始…dp在acm比赛中非常重要,一定要学好

0 0
原创粉丝点击