poj1717 Dominoes (背包)
来源:互联网 发布:linux dhcp server 编辑:程序博客网 时间:2024/05/21 22:54
Dominoes
Time Limit: 1000MSMemory Limit: 65536KTotal Submissions: 6665Accepted: 2211
Description
A domino is a flat, thumbsized tile, the face of which is divided into two squares, each left blank or bearing from one to six dots. There is a row of dominoes laid out on a table:
The number of dots in the top line is 6+1+1+1=9 and the number of dots in the bottom line is 1+5+3+2=11. The gap between the top line and the bottom line is 2. The gap is the absolute value of difference between two sums.
Each domino can be turned by 180 degrees keeping its face always upwards.
What is the smallest number of turns needed to minimise the gap between the top line and the bottom line?
For the figure above it is sufficient to turn the last domino in the row in order to decrease the gap to 0. In this case the answer is 1.
Write a program that: computes the smallest number of turns needed to minimise the gap between the top line and the bottom line.
The number of dots in the top line is 6+1+1+1=9 and the number of dots in the bottom line is 1+5+3+2=11. The gap between the top line and the bottom line is 2. The gap is the absolute value of difference between two sums.
Each domino can be turned by 180 degrees keeping its face always upwards.
What is the smallest number of turns needed to minimise the gap between the top line and the bottom line?
For the figure above it is sufficient to turn the last domino in the row in order to decrease the gap to 0. In this case the answer is 1.
Write a program that: computes the smallest number of turns needed to minimise the gap between the top line and the bottom line.
Input
The first line of the input contains an integer n, 1 <= n <= 1000. This is the number of dominoes laid out on the table.
Each of the next n lines contains two integers a, b separated by a single space, 0 <= a, b <= 6. The integers a and b written in the line i + 1 of the input file, 1 <= i <= 1000, are the numbers of dots on the i-th domino in the row, respectively, in the top line and in the bottom one.
Each of the next n lines contains two integers a, b separated by a single space, 0 <= a, b <= 6. The integers a and b written in the line i + 1 of the input file, 1 <= i <= 1000, are the numbers of dots on the i-th domino in the row, respectively, in the top line and in the bottom one.
Output
Output the smallest number of turns needed to minimise the gap between the top line and the bottom line.
Sample Input
4
6 1
1 5
1 3
1 2
Sample Output
1
Source
CEOI 1997
这道题就是说麻将可以上下翻动,是使得上下点数和的差最小的时候最少的翻转步数。
第一种方法,我们把每一个的上下差值作为容量,我们每取一个容量,价值就加1,由此可以转化为01背包。
/************************** *Create time: Mon Aug 01 09:04:35 2016 *Author: Mymilkbottles *File name: POJ1717**************************/#include<iostream>using namespace std;#include<cstdio>#include<cstring>#include<algorithm>#include<cmath>#include<stdlib.h>#include<vector>#include<queue>#include<deque>#include<map>#include<set>#include<time.h>#define pi(x,y) printf("%d%c",(x),(y));#define pin(x) printf("%d\n",(x));#define si(x) scanf("%d",&(x))#define sii(x,y) scanf("%d%d",&(x),&(y))#define s3(x,y,z) scanf("%d%d%d",&(x),&(y),&(z))#define rep(x,y,z) for(int (x)=(y);(x)<(z);++(x))#define dep(x,y,z) for(int (x)=(y)-1;(x)>=(z);--(x))#define read int TcaseN;scanf("%d",&TcaseN);for(int Tcase=1;Tcase<=TcaseN;++Tcase)#define cls(x,y) memset((x),(y),sizeof((x)));#define pb(x) push_back(x)#define mp(x,y) make_pair((x),(y))#define max3(value_a,value_b,value_c) max(max(value_a,value_b),value_c)#define min3(value_a,value_b,value_c) min(min(value_a,value_b),value_c)#define GT(x) (x)=clock();///In This You Can Define Long Integer Type#define LONGTYPE long longtypedef LONGTYPE LL;typedef unsigned LONGTYPE ULL;const int maxint=((~((unsigned)(0)))>>1);const LL maxll=((~((unsigned LONGTYPE)(0)))>>1);const int inf=0x3f3f3f3f;const double PI=acos(-1.0);const int maxn=1e4+5008;const int mid=7002;const int maxm=1005;int dp[maxn];int a[maxm];inline int mins(int aa,int bb) { return aa<bb?aa:bb;}int main() {#ifdef tangge clock_t tSTART,tEND,t3; GT(tSTART);#endif // tangge int n,u,v,sum=0,fi=0; while(~si(n)) { fi=sum=0; rep(i,0,n) { sii(u,v); fi+=u,sum+=(u+v),a[i]=u-v; } if((fi<<1)==sum) { puts("0"); continue; } cls(dp,inf) dp[mid]=0; rep(i,0,n) { if(a[i]>0) { dep(j,sum+mid+1,a[i]) { if(dp[j-a[i]]^inf)dp[j]=mins(dp[j],dp[j-a[i]]+1); } } else { rep(j,0,sum+mid-a[i]+1) { if(dp[j-a[i]]^inf) { dp[j]=mins(dp[j],dp[j-a[i]]+1); } } } } int t=inf,ans=inf,fl; rep(i,0,sum+mid+1) { if(dp[i]==inf) continue; fl=abs((fi-i+mid)-(sum-(fi-i+mid))); if(t>fl) { t=fl; ans=dp[i]; } else if(t==fl&&ans>dp[i]) { ans=dp[i]; } } printf("%d\n",ans); }#ifdef tangge GT(tEND); printf("%.8lf\n",(tEND-tSTART)/1000.0);#endif // tangge return 0;}
第二种方法:
我们可以使用分组背包解决,一共n组,每组选一个且必须选一个。
有一个地方,状态转移的时候我们是+k而不是+1,因为我们选的是上下面的,我们不是两种情况都需要翻转。
/************************** *Create time: Mon Aug 01 10:58:29 2016 *Author: Mymilkbottles *File name: POJ1717.1.cpp**************************/#include<iostream>using namespace std;#include<cstdio>#include<cstring>#include<algorithm>#include<cmath>#include<stdlib.h>#include<vector>#include<queue>#include<deque>#include<map>#include<set>#include<time.h>#define pi(x,y) printf("%d%c",(x),(y));#define pin(x) printf("%d\n",(x));#define si(x) scanf("%d",&(x))#define sii(x,y) scanf("%d%d",&(x),&(y))#define s3(x,y,z) scanf("%d%d%d",&(x),&(y),&(z))#define rep(x,y,z) for(int (x)=(y);(x)<(z);++(x))#define dep(x,y,z) for(int (x)=(y)-1;(x)>=(z);--(x))#define read int TcaseN;scanf("%d",&TcaseN);for(int Tcase=1;Tcase<=TcaseN;++Tcase)#define cls(x,y) memset((x),(y),sizeof((x)));#define pb(x) push_back(x)#define mp(x,y) make_pair((x),(y))#define max3(value_a,value_b,value_c) max(max(value_a,value_b),value_c)#define min3(value_a,value_b,value_c) min(min(value_a,value_b),value_c)#define GT(x) (x)=clock();///In This You Can Define Long Integer Type#define LONGTYPE long longtypedef LONGTYPE LL;typedef unsigned LONGTYPE ULL;const int maxint=((~((unsigned)(0)))>>1);const LL maxll=((~((unsigned LONGTYPE)(0)))>>1);const int inf=0x3f3f3f3f;const double PI=acos(-1.0);const int maxn=1e3+5;int a[2][maxn];int dp[maxn][maxn*6];int main() {#ifdef tangge clock_t tSTART,tEND,t3; GT(tSTART);#endif // tangge int n,sum,fl; while(~si(n)) { sum=0; rep(i,1,n+1) { sii(a[0][i],a[1][i]); sum+=a[0][i],sum+=a[1][i]; } cls(dp,-1) dp[0][0]=0; rep(i,1,n+1) { dep(j,sum+1,0) { rep(k,0,2) { if(j<a[k][i]) continue; if(dp[i-1][j-a[k][i]]^-1) { dp[i][j]=(dp[i][j]==-1)?(dp[i-1][j-a[k][i]]+k):min(dp[i-1][j-a[k][i]]+k,dp[i][j]); }//if(dp[i][j]^-1)cout<<"i="<<i<<" j="<<j<<" k="<<k<<" dp="<<dp[i][j]<<" dp="<<dp[i-1][j-a[k][i]]<<endl;; } } } int tv=inf,ans=inf; rep(i,0,sum+1) { if(dp[n][i]<0)continue; fl=abs(i-(sum-i)); if(tv>fl) { ans=dp[n][i];//min(dp[n][i],n-dp[n][i]); tv=fl; } else if(tv==fl) ans=min(dp[n][i],ans);//min(ans,min(dp[n][i],n-dp[n][i])); } pin(ans); }#ifdef tangge GT(tEND); printf("%.8lf\n",(tEND-tSTART)/1000.0);#endif // tangge return 0;}
这是二维的,我们可以优化成一维的,会快很多。
/************************** *Create time: Mon Aug 01 10:58:29 2016 *Author: Mymilkbottles *File name: POJ1717.1.cpp**************************/#include<iostream>using namespace std;#include<cstdio>#include<cstring>#include<algorithm>#include<cmath>#include<stdlib.h>#include<vector>#include<queue>#include<deque>#include<map>#include<set>#include<time.h>#define pi(x,y) printf("%d%c",(x),(y));#define pin(x) printf("%d\n",(x));#define si(x) scanf("%d",&(x))#define sii(x,y) scanf("%d%d",&(x),&(y))#define s3(x,y,z) scanf("%d%d%d",&(x),&(y),&(z))#define rep(x,y,z) for(int (x)=(y);(x)<(z);++(x))#define dep(x,y,z) for(int (x)=(y)-1;(x)>=(z);--(x))#define read int TcaseN;scanf("%d",&TcaseN);for(int Tcase=1;Tcase<=TcaseN;++Tcase)#define cls(x,y) memset((x),(y),sizeof((x)));#define pb(x) push_back(x)#define mp(x,y) make_pair((x),(y))#define max3(value_a,value_b,value_c) max(max(value_a,value_b),value_c)#define min3(value_a,value_b,value_c) min(min(value_a,value_b),value_c)#define GT(x) (x)=clock();///In This You Can Define Long Integer Type#define LONGTYPE long longtypedef LONGTYPE LL;typedef unsigned LONGTYPE ULL;const int maxint=((~((unsigned)(0)))>>1);const LL maxll=((~((unsigned LONGTYPE)(0)))>>1);const int inf=0x3f3f3f3f;const double PI=acos(-1.0);const int maxn=1e3+5;int dp[12005];int main() {#ifdef tangge clock_t tSTART,tEND,t3; GT(tSTART);#endif // tangge int n,sum,fl,u,v; si(n); { sum=0; cls(dp,-1) dp[0]=0; rep(i,1,n+1) { sii(u,v); sum+=u+v; dep(j,sum+1,0) { if(dp[j]^-1) { int t=dp[j]; dp[j]=-1; if(dp[j+u]==-1||dp[j+u]>t) { dp[j+u]=t; } if(dp[j+v]==-1||dp[j+v]>t+1) { dp[j+v]=t+1; } } } } sum/=2; int i, j; for(i = sum; i >= 0; i--) { if(dp[i] != -1) break; } for(j = sum; j < 12005; j++) { if(dp[j] != -1) break; } printf("%d\n", dp[i] > dp[j] ? dp[j] : dp[i]);// int f1,f2;// rep(i,sum,maxn){// if(dp[i]^-1){// f1=dp[i];break;// }// }// dep(i,sum+1,0){// if(dp[i]^-1){// f2=dp[i];break;// }// }// pin(min(f1,f2));// int tv=inf,ans=inf;// rep(i,0,sum+1){// if(dp[i]^-1){// int t=abs(i-sum+i);// if(tv>t){// ans=dp[i];// tv=t;// }else if(tv==t)ans=min(ans,dp[i]);// }// }// pin(ans); }#ifdef tangge GT(tEND); printf("%.8lf\n",(tEND-tSTART)/1000.0);#endif // tangge return 0;}
1 0
- POJ1717 Dominoes (背包)
- poj1717 Dominoes (背包)
- POJ1717 Dominoes DP,背包的变形
- [POJ1717]Dominoes(dp)
- [POJ1717][luogu1282]Dominoes(多米诺骨牌)(dp)
- poj1717&&vijos p1222(背包变形)
- poj 1717 Dominoes 背包
- [Poj1717]&[洛谷1282]多米诺骨牌 背包Dp
- poj 1717 Dominoes 01背包
- Dominoes
- poj1717 DP
- pku1717 Dominoes
- Tiling Dominoes
- uva11270Tiling Dominoes
- Long Dominoes
- Dominoes-第一个回溯
- poj 1717 Dominoes
- poj 1717 Dominoes
- Java Advanced Management Console简介
- ubuntu下安装quagga-0.99.19.tar.gz
- 编写Jquery -- 简单版 查找元素
- (LeetCode)Add Digits --- 整数各位相加
- 关于Linux内核开发的问题,觉得可以分享下
- poj1717 Dominoes (背包)
- 中文字符与英文字符所占字节
- Xcode The certificate used to sign "xxx" has either expired or has been revoked. An updated certif
- 取消iOS对图片的渲染
- sass学习笔记
- 【Git/Github学习笔记】Git分支管理(一)
- sql分页查询
- android 长图显示模糊问题
- 更改UIAlertAction的字体颜色