poj 1285简单的组合
来源:互联网 发布:图书购买系统c语言 编辑:程序博客网 时间:2024/05/17 03:08
这道题第一遍看觉得是有公式的,但是用动态规划更加简单啦!简单说一下我的思路:
首先将输入的数组进行排序
建立一个数组b[i][j]表示从第i个元素开始(包括i)中抽取j个数的不同的种类数
则b[i][j]=b[i+1][j-1]+b[x][j]
b[i+1][j-1]:代表将第i个数取出,那么剩下的就是求从i+1个元素开始种去j-1个数的不同种类数
b[x][j]:代表第i个数没有取,因为数组中有数重复,而且数组又是排过序的,则x代表的是从第i个元素之后不等于第i个元素的第一个数,
本题的大致思路就是这个,这个思路也是从别人那里借鉴了一下,以后得提高自己分析问题的能力啊!
超时的代码:这个代码是我用纯粹的递归写的,然后针对每个输入的r都递归一次,结果超时了,所以以后要总结经验,有的时候有更好的方法就不能使用递归的!
#include<iostream>#include<algorithm>using namespace std;int a[55],n,m;int cmp(const void *a,const void *b){return *(int *)a-*(int *)b;}unsigned __int64 fun(int m, int r){if(m>n)return 0;if(r==0)return 1; int i;i=m;while(a[i]==a[m])//找到和那个和a[m]不相同的第一个值得i++;if(i<=n)return fun(m+1,r-1)+fun(i,r);elsereturn fun(m+1,r-1);}int main(){ int i,j,r,k=0;while(1){//cin>>n>>m;scanf("%d%d",&n,&m);if(n==0)break;for(i=0; i<n; i++)scanf("%d",&a[i]);qsort(a,n,sizeof(int),cmp);k++;printf("Case %d:\n",k);for(j=0;j<m; j++){scanf("%d",&r);unsigned __int64 m=fun(0,r);printf("%I64d\n",m);}}return 0;}
改进的算法:将所算的的结果存储在二维数组中,对于一组输入数据,先找出需要求的最大的组合数,针对它进行求解,则比它小的数就可以直接从二维数组里面取得结果啦!
代码如下(这个代码的效率相当高啦!哈哈):
#include<iostream>#include<algorithm>using namespace std;int a[55],n,m;unsigned __int64 b[55][55];int cmp(const void *a,const void *b){return *(int *)a-*(int *)b;}unsigned __int64 fun(int m, int r){if(m>=n)return 0; int i;i=m;while(a[i]==a[m])//找到和那个和a[m]不相同的第一个值得i++;if(i<=n)b[m][r]=b[m+1][r-1]+fun(i,r);//return fun(m+1,r-1)+fun(i,r);elseb[m][r]=b[m+1][r-1];//return fun(m+1,r-1);return b[m][r];}int main(){ int i,j,r,k=0; int c[55];while(1){//cin>>n>>m;scanf("%d%d",&n,&m);if(n==0)break;for(i=0; i<n; i++)scanf("%d",&a[i]);qsort(a,n,sizeof(int),cmp);k++;for(i=0; i<=n; i++){b[i][0]=1; for(j=1; j<=n; j++)b[i][j]=0;}printf("Case %d:\n",k);int ma=0;for(j=0;j<m; j++){scanf("%d",&c[j]);if(c[j]>ma)ma=c[j]; }for(i=1; i<=ma; i++)for(j=0; j<n; j++) fun(j,i);//取最大的进行求值的for(j=0; j<m; j++)printf("%I64d\n",b[0][c[j]]);}return 0;}
- poj 1285简单的组合
- POJ 1753 (组合+递归) Flip game 简单易懂的源代码
- 简单的组合动画
- ACM中的【数学知识】之【组合数学】(一) Polya定理的简单理解 POJ 1286
- 组合模式的简单应用
- Verilog简单的组合逻辑设计
- 简单的自定义组合控件
- POJ-3364(简单组合)(Black and white painting )
- POJ 1942 Paths on a Grid(简单组合数学)
- poj 1942 走地图的组合数学
- 简单组合
- 对象的组合的简单例题
- 超简单的组合排列问题
- nhibernate学习之简单组合的映射
- nhibernate学习之简单组合的映射
- 简单的限定个数组合生成 Combinations
- JAVA各种类的简单组合
- Group Box组合框的简单使用
- js-window对象的方法和属性资料
- NSStringFromSelector(_cmd))
- k
- 喜欢的名言
- 虚拟化计算机的应用前景
- poj 1285简单的组合
- c函数返回指针
- android中的listView使用小结
- winform键盘事件的响应(C#,winform)
- 【iOS知识学习】_关键字self,super,copy, retain, readonly , readwrite, nonatomic、@synthesize、@property
- 细说 #pragma pack(n)*** #pragma pack(push,1)与#pragma pack(1)的区别
- mongodb-2.2.2 with v8-3.16.9 and jemalloc-3.2.0 at centos5.X|6.X install 一键安装脚本
- fedora 17 中安装libperl-dev
- 关于BinaryWriter或者BinaryReader中的编码和流字节序问题