随笔分类 - 动态规划
ACM重点
摘要:dp[i]代表抢到i的钱且不被抓住的最大概率1-dp[i]就是被抓住的最小概率easy~#include<stdio.h>#include<string.h>double a[110],dp[10010];int m[110];double max(double a,double b){ return a>b?a:b;}int main(){ int t,i,j,n,k; double P; scanf("%d",&t); while(t--) { scanf("%lf%d",&P,&n); int
阅读全文
摘要:注意,求的是最大的概率,所以先求出不能被录取的最小的概率p,然后直接1-p即可WA了两次原因:初始化的时候dp[0]没有赋值#include<stdio.h>#include<string.h>double dp[10010];int a[1010];double b[1010];double min(double a,double b){ return a<b?a:b;}int main(){ int n,m,i,j,k; while(scanf("%d%d",&n,&m),(n||m)) { for(i=1;i<=m;
阅读全文
摘要:题目看了好久,囧!dp[i][j]表示前i节车厢用j个火车头去拉所能拉的最大乘客量#include<stdio.h>#include<string.h>int dp[55555][4],a[55555];int max(int a,int b){ return a>b?a:b;}int main(){ int t,i,j,k,n,m; scanf("%d",&t); while(t--) { scanf("%d",&n); a[0]=0; for(i=1;i<=n;i++) scanf("%d
阅读全文
摘要:dp[i][j]代表能否组成一边长为i和一边长为j的三角形,剩下的一边就是sum-i-j了接下来就是背包的做法了#include<stdio.h>#include<math.h>#include<string.h>bool dp[810][810];int get_area(int x,int y,int z){ double p=(x+y+z)/2.0; return int(sqrt(p*(p-x)*(p-y)*(p-z))*100);}int max(int a,int b){ return a>b?a:b;}int a[50];int main
阅读全文
摘要:有个小技巧,因为力矩可能为负数,就把所有的力矩都加上一个值(加上后保证为正数就好),最后输出组成这个数的方案数#include<stdio.h>#include<string.h>int pos[30],w[30];int dp[21][4000];int main(){ int C,G; int i,j,k; scanf("%d%d",&C,&G); for(i=1;i<=C;i++) scanf("%d",&pos[i]); for(i=1;i<=G;i++) scanf("%d&
阅读全文
摘要:把取余神马的都提前处理掉,可以加快速度(bool)dp[i][j]=dp[i-1][j-a[i]]||dp[i-1][j+a[i]]#include<stdio.h>#include<string.h>int a[10001];bool dp[10001][101];int n,m;int main(){ int i,j; scanf("%d%d",&n,&m); for(i=1;i<=n;i++) { scanf("%d",&a[i]); while(a[i]<0) a[i]+=m; a[i]
阅读全文
摘要:#include<stdio.h>#include<string.h>int m,n;char str[15][15];int col[110][22];bool dp[200000];int t[110],s[110],g[110][110];int getid(char *s){ for(int i=0;i<m;i++) if(strcmp(s,str[i])==0) return i; return 0;}int main(){ int i,j,k; char tmp[15]; while(scanf("%d%d",&m,&
阅读全文
摘要:bug:忘了给dp[0]赋值为1了#include<stdio.h>#include<string.h>bool dp[20000000];int h[22];int main(){ int n,b,i,j,sum=0; scanf("%d%d",&n,&b); for(i=1;i<=n;i++) { scanf("%d",&h[i]); sum+=h[i]; } memset(dp,0,sizeof(dp));dp[0]=1; for(i=1;i<=n;i++) { for(j=sum;j&g
阅读全文
摘要:背包入门题。。View Code 1 #include<stdio.h> 2 #include<string.h> 3 int dp[12885]; 4 int max(int a,int b) 5 { 6 return a>b?a:b; 7 } 8 int main() 9 {10 int n,m,i,j,w,v;11 while(scanf("%d%d",&n,&m)!=EOF)12 {13 memset(dp,0,sizeof(dp));14 for(i=1;i<=n;i++)15 {16 ...
阅读全文
摘要:#include<stdio.h>#include<string.h>int a[510],b[510];int dp[510];int main(){ int t,m,n,i,j; scanf("%d",&t); while(t--) { scanf("%d",&m); for(i=1;i<=m;i++) scanf("%d",&a[i]); scanf("%d",&n); for(i=1;i<=n;i++) scanf("%d&quo
阅读全文
摘要:这两题基本是一样的,模拟球队之间对战、晋级,整个过程就是一颗满二叉树,最终根节点的位置就是冠军这道题目有一个很神奇的地方,改天我会仔细解释,现在先留着代码View Code 1 #include<stdio.h> 2 #include<string.h> 3 double p[130][130]; 4 double dp[130][8]; 5 int main(){ 6 int i,j,t,cases=1; 7 char str[20][20]; 8 scanf("%d",&t); 9 while(t--){10 for(i=0;i<1
阅读全文
摘要:转自http://blog.csdn.net/morgan_xww/article/details/6774708http://blog.csdn.net/xymscau/article/details/6601262对随机变量A、B,有数学期望E(aA+bB)=aE(A)+bE(b);有了这个公式你就可以进行将连续的期望问题,转化为独立的状态了,概率就相当于a,b;A,B为变量,那么来分析一下这个问题,对于下一次查找,只可能有4种状态的转移,找到bugs,找到subcomponents,都找到和都找不到。因为e[i][j]=p1*e[i+1][j]+p2*e[i][j+1]+p3*e[i+1
阅读全文
摘要:不怎么会做这类题目额。。伤,看别人的View Code 1 #include<stdio.h> 2 #include<string.h> 3 #define maxn 1010 4 int dp[maxn][maxn]; 5 int sum[maxn][maxn]; 6 const int mod = 1000000007; 7 int main() 8 { 9 int i,j;10 char s[maxn];11 while(scanf("%s",s)!=EOF)12 {13 int n=strlen(s);14 memset...
阅读全文
摘要:dp[i]表示现在存在i个吸血鬼要达成目标(全为吸血鬼)天数的数学期望假如现在再增加一天,这一天可能会增加一个吸血鬼,p1*(dp[i+1]+1)表示接下来的一天增加了一个吸血鬼,所以为(dp[i+1]+1),还有一种可能就是没有增加吸血鬼,概率自然是(1-p1)dp[i]+1表示接下来的一天没有增加吸血鬼,但向后推移了一天因此dp[i]这个状态可以转移到dp[i+1]+1,概率为p1dp[i]+1 概率为(1-p1)所以dp[i]=(dp[i+1]+1)*p1+(dp[i]+1)*(1-p1);p1是有i个吸血鬼再增加一个的概率就是说一个人和一个吸血鬼相遇,且人成功变成吸血鬼的概率为(n-i
阅读全文
摘要:表示原来用RMQ和LCA做的方法烦了,现在直接在建最小生成树的过程中建双向边就好了, cost[i][j]表示i到j的最长树边View Code 1 #include<string.h> 2 #include<stdio.h> 3 #include<vector> 4 #include<math.h> 5 #include<queue> 6 using namespace std; 7 const int M =1010; 8 const double inf = 1e20; 9 double max(double a,double
阅读全文
摘要:二分一个分段数,再用RMQ累加区间最值,跑的好慢哦#include<stdio.h>#include<string.h>const int MAX = 200010;#define min(a,b) a<b?a:b#define max(a,b) a>b?a:bint dp[MAX][30],a[MAX];int k;void init(int n){ memset(dp,0,sizeof(dp)); int i,j,m; for(i=1;i<=n;i++) { dp[i][0]=a[i]; } for(j=1,m=1;m<=n;m<<
阅读全文
摘要:View Code dp[i][j]>?=dp[i][k]+dp[k+1][j];if(s[i]=='('&&s[j]==')'||s[i]=='['&&s[j]==']') dp[i][j]=max(dp[i][j],dp[i+1][j-1]+2);转移过程#include<stdio.h>#include<string.h>#define max(a,b) a>b?a:bint dp[110][101];char s[110];int main(){ char
阅读全文
摘要:其实不管什么DP,本质思想都是不变的,围绕着最优子结构展开思路,最终记录下最优的结果,所以写好状态转移,处理好边界问题,还是关键手段。状态:dp[i][j]表示以i为根的子树孤立出 j 个点要去掉的最少的边,在树上的动态规划一般都是父结点和子节点的关系,所以在思考状态转移时时应该尽量把父结点的子节点考虑进去分别以不同的点为根进行深搜先要想到我们最后要得到的结果应该是dp[i][p]中的最小值而dp[i][j]是从dp[u][k]和dp[i][j-k]推过来的,u为i的子节点还有就是以i为根和以i的子节点为u根时,dp[u][k]+dp[i][j-k]多加了两次他们之间的边,所以要减去2即dp[
阅读全文
摘要:View Code //dp[i]表示以第i个长方体结尾的最大高度(先排好序的)//虽说不难,但一些细节能让人崩溃,以后一定要注意//刚开始想到的状态为前i个长方体所能产生的最大高度,但亲注意://ps:这是比赛时想到的状态,悲剧就是这么发生的//如果dp[i]如上定义,那么当用第i个长方体往前覆盖时,应该在原来的路径上覆盖,而不是从i-1->1;//因此这种方法正确性貌似有待证明#include<stdio.h>#include<string.h>#include<algorithm>using namespace std;__int64 dp[10
阅读全文
摘要:Strategic gameTime Limit:2000MS Memory Limit:65536KTotal Submit:33 Accepted:15Description Bob enjoys playing computer games, especially strategic games, but sometimes he cannot find the solution fast enough and then he is very sad. Now he has the following problem. He must defend a medieval city, th
阅读全文

浙公网安备 33010602011771号