母函数的初识——本拉登 hdu 1085
2017-12-22 20:54
309 查看
题目链接 :母函数——本拉登
母函数 用多重的情况
一个充分利用数学原理的方法
强大的暴力算法
古老的dp算法
#include <iostream> #include <cstdio> #include <algorithm> using namespace std; int num[10] ; int c1[100000] , c2[100000] ; int main() { int i,j,k; while(cin >> num[1] >> num[2] >> num[5] && num[1] || num[2] || num[5]) { int MAX = num[1] + num[2]*2 + num[5]*5;// 定义了一个max是为了减少运算量 // 照常进行初始化 for(i = 0;i <= MAX;i ++){ c1[i] = 0; c2[i] = 0; } // 第一步 进行第一个数据的运算 for(i = 0;i <= num[1];i ++) c1[i] = 1 ; // 第二步 进行(1+x1+x2....)*(1+x2+x4...)的运算 for(i = 0;i <= num[1];i ++){ for(j = 0;j <= num[2]*2;j += 2) c2[j + i] += c1[i]; } // 运算结束时,进行赋值和清空。 for(i = 0;i <= num[1] + num[2]*2;i ++){ c1[i] = c2[i]; c2[i] = 0; } // 第三步 进行前面值的乘加 for(i = 0;i <= num[1] + num[2]*2;i ++) for(j = 0;j <= num[5]*5;j += 5){ c2[i + j] += c1[i]; } // 把临时变量的值给赋值,感觉并没有什么用处的 for(i = 0;i <= MAX;i ++){ c1[i] = c2[i]; c2[i] = 0; } for(i = 0;i <= MAX;i ++) if( !c1[i] ){ printf( "%d\n" , i ) ; break ; } if( i == MAX + 1 ) printf( "%d\n" , i ) ; } return 0 ; }
母函数 用多重的情况
/* * Author: illuz <iilluzen[at]gmail.com> * File: 1085.cpp * Create Date: 2014-05-25 11:34:37 * Descripton: Generating Function */ #include <cstdio> #include <cstring> const int N = 1e4; int val[3] = {1, 2, 5}, cnt[3]; int c1 , c2 , mmax; int main() { while (~scanf("%d%d%d", &cnt[0], &cnt[1], &cnt[2]) && (cnt[0] || cnt[1] || cnt[2])) { memset(c1, 0, sizeof(c1)); memset(c2, 0, sizeof(c2)); mmax = 0; for (int i = 0; i < 3; i++) mmax += cnt[i] * val[i]; for (int i = 0; i <= cnt[0]; i++) // 处理第一种硬币 c1[i] = 1; for (int i = 1; i < 3; i++) { // 对于1后面的每种硬币 for (int j = 0; j <= mmax; j++) { if (c1[j] != 0) { // 对于之前的项(c1) for (int k = 0; k <= val[i] * cnt[i]; k += val[i]) { // 模拟与当前项式相乘 if (j + k <= mmax) c2[j + k] += c1[j]; } } } // 把当前项保存在c1,清空c2 memcpy(c1, c2, sizeof(c1)); memset(c2, 0, sizeof(c2)); } int i; for (i = 0; i <= mmax; i++) { if (c1[i] == 0) break; } printf("%d\n", i); } return 0; }
一个充分利用数学原理的方法
#include <stdio.h> int main() { int o,t,f,min; while(1) { scanf("%d %d %d",&o,&t,&f); if (!(o || t || f)) break; if(!o) min=1; else { if(o + 2*t < 4) min = (o + 2*t) + 1; else min = o + 2*t + 5*f + 1; } printf("%d\n",min); } return 0; }
强大的暴力算法
#include <iostream> #include <cstring> using namespace std; int a[10000]; int main()//暴力方法 { int n,m,l; while(cin >> n >> m >> l){ if (n + m + l == 0) break; memset(a,0,sizeof(a)); for (int i = 0;i <= n;i ++){ for (int j = 0;j <= m;j ++){ for (int k = 0;k <= l;k ++){ a[i*1 + j*2 + k*5]=1; } } } for(int k = 1;k <= 8001;k ++){//这里不能用sum if(!a[k]){ cout << k << endl; break; } } } return 0; }
古老的dp算法
#include<iostream> #include<cstring> using namespace std; int a[8005]; int main()//DP { int num[3],v[3] = {1,2,5}; while(cin >> num[0] >> num[1] >> num[2]){ if (num[0] == 0 && num[1] == 0 && num[2] == 0) break; memset(a,0,sizeof(a)); int k,sum = 0; for(int i = 0;i < 3;i ++){ sum += num[i]*v[i];//计算最大数值 } //cout<<sum<<endl; a[0] = 1; for(int i = 0;i < 3;i ++){//DP算法 for(int k = sum;k >= v[i];k --){ for(int j = 1;j <= num[i];j ++){ if(k-v[i]*j >= 0) a[k] = a[k-v[i]*j];//当前状态取决于前一状态 } } } for(int k = 1;k <= sum+1;k ++){//这里不能用sum if(!a[k]){ cout << k << endl; break; } } } return 0; }
相关文章推荐
- HDU 1085 Holding Bin-Laden Captive! 活捉本拉登(普通型母函数)
- hdu 1085 Holding Bin-Laden Captive! (母函数)
- hdu 1085 母函数
- HDU 1085 母函数/思维
- hdu 1085 Holding Bin-Laden Captive! (母函数)
- HDU 1085 Holding Bin-Laden Captive!(母函数)
- HDU 1085 Holding Bin-Laden Captive!(母函数)
- [母函数]HDU 1085 Holding Bin-Laden Captive!
- HDU 1085 母函数
- HDU1085(母函数模板)
- [HDU 1085] Holding Bin-Laden Captive! 母函数或多重背包
- HDOJ/HDU 1085 Holding Bin-Laden Captive!(非母函数求解)
- hdu 1085 Holding Bin-Laden Captive!(母函数)
- [ACM] hdu 1085 Holding Bin-Laden Captive! (母函数变形)
- HDU 1085 Holding Bin-Laden Captive! 母函数
- HDU - 1085 Holding Bin-Laden Captive!(母函数)
- HDU 1085(dp 母函数)
- HDOJ/HDU 1085 Holding Bin-Laden Captive!(非母函数求解)
- hdu 1085 Holding Bin-Laden Captive!(母函数)
- hdu1085 母函数(初始化问题很重要)