Problem Description
"Well, it seems the first problem is too easy. I will let you know how foolish you are later." feng5166 says.
"The second problem is, given an positive integer N, we define an equation like this:
  N=a[1]+a[2]+a[3]+...+a[m];
  a[i]>0,1<=m<=N;
My question is how many different equations you can find for a given N.
For example, assume N is 4, we can find:
  4 = 4;
  4 = 3 + 1;
  4 = 2 + 2;
  4 = 2 + 1 + 1;
  4 = 1 + 1 + 1 + 1;
so the result is 5 when N is 4. Note that "4 = 3 + 1" and "4 = 1 + 3" is the same in this problem. Now, you do it!"
Input
The input contains several test cases. Each test case contains a positive integer N(1<=N<=120) which is mentioned above. The input is terminated by the end of file.
Output
For each test case, you have to output a line contains an integer P which indicate the different equations you have found.
Sample Input
4
10
20
Sample Output
5
42
627
解题思路:这题既可以用动态规划,也可以用母函数。
DP原先是递归而来的,这里就直接讲递推吧!
(整数划分有很多种,这里属于划分的多个整数可以相同)
首先定义dp[i][j]记录将整数i划分成所有元素都不大于j的所有情况数,下面举个栗子:
当i=4,j=1时,要求划分得到的所有元素都不大于j,所以划分法只有1种:{1,1,1,1};
当i=4,j=2时,。。。。。。。。。。。。。。。。。。。。。只有2种:{1,1,1,1},{2,1,1},{2,2};
当i=4,j=3时,。。。。。。。。。。。。。。。。。。。。。只有3种:{1,1,1,1},{2,1,1},{2,2},{3,1};
当i=4,j=4时,。。。。。。。。。。。。。。。。。。。。。只有4种:{1,1,1,1},{2,1,1},{2,2},{3,1},{4};
当i=4,j=5,6.....n(n为自然数)时,。。。。。。。。。。只有4种:{1,1,1,1},{2,1,1},{2,2},{3,1},{4};
从以上规律可以推出结论:当i==1||j==1,只有一种划分法;
一、当i<j时,由于分法不可能出现负数,所以dp[i][j]=dp[i][i];
二、当i==j时,分两种情况:①如果要划分出j这一个数,那么情况只有1种:{j};②如果不分,那么就将i分成所有元素不大于j-1的若干份,dp[i][j]=dp[i][j-1]。所以总的情况数为dp[i][j]=dp[i][j-1]+1;
三、当i>j时,也分两种情况:①如果要划分出j这一个数,注意此时的j<i,说明其剩下的整数(i-j)划分成的所有元素都在这个集合{j,a1,a2...}里,那么此时的dp[i][j]为把剩下的(i-j)这个整数划分成所有元素都不大于j时的情况数,即dp[i][j]=dp[i-j][j];②如果不分,那么就将i分成所有元素不大于j-1的若干份,dp[i][j]=dp[i][j-1]。所以总的情况数为dp[i][j]=dp[i-j][j]+dp[i][j-1]。
AC代码一之计数DP:
 #include<bits/stdc++.h>
using namespace std;
typedef long long LL;
const int maxn = ;
LL dp[maxn][maxn];int n;//dp[i][j]记录将整数i划分成所有元素不大于j的所有情况数
int main()
{//打表
for(int i=;i<maxn;i++)//将整数i划分成所有元素不大于1的分法和将整数1划分成所有元素不大于i(其实只有1本身)的分法都为1种
dp[i][]=dp[][i]=;
for(int i=;i<maxn;i++){//从划分2份开始
for(int j=;j<maxn;j++){//从整数2开始划分
if(i<j)dp[i][j]=dp[i][i];
else if(i==j)dp[i][j]=dp[i][j-]+;
else dp[i][j]=dp[i][j-]+dp[i-j][j];
}
}
while(cin>>n){
cout<<dp[n][n]<<endl;//最后输出总的情况数,即将整数n划分成不大于n的所有情况数
}
return ;
}

AC代码二:关于这种解法可以看看这篇博文:题解报告:hdu 1284 钱币兑换问题(简单数学orDP)

 #include<bits/stdc++.h>
using namespace std;
typedef long long LL;
int main(){
LL n,dp[]={};//预处理打表
for(int i=;i<;++i)
for(int j=i;j<;++j)//每种数字可以看作无限个--->完全背包
dp[j]+=dp[j-i];
while(cin>>n){cout<<dp[n]<<endl;}
return ;
}

母函数解法,先贴一篇入门博文:母函数简介,看完后再看一篇:母函数的应用。普通型母函数其实就是把复杂的分类和分步求和过程具体为一个可以求解的"函数":通过将简单的构造(生成)函数展开多项式后可以发现一个规律:指数代表和数,每一项的系数代表凑成那一项指数的方案总数,实际上这就是多重集组合问题的求解答案。每个多项式中每一项前面的系数都为1,表示每种情况都有1种出现的可能。因此,我们只需构造出正确的生成函数,编程时通过模拟多个多项式相乘即可。对于此题构造出的生成函数就是G(x)=(1+x^1+x^2..+x^n)(1+x^2+x^4+x^6+...)(1+x^3+x^6+...)(...)(1+x^n),从这个"函数"中可以看出每一个多项式中有着完全背包的思想,即不取或取一件或取多件。注意:由于要求的是凑成和为n的方案数,所以多项式中每一项相乘得到的指数应不超过n,最终x^n前面的系数就是整数n的划分总方案数。

AC代码三:时间复杂度为O(n3)。

 #include<bits/stdc++.h>
using namespace std;
const int maxn=;
int n,c1[maxn],c2[maxn];
int main(){
while(~scanf("%d",&n)){
memset(c1,,sizeof(c1));//c1[ ]保存当前得到的多项式各项系数,c2[ ]保存每次计算时的各项系数的临时结果,并且每计算完一个多项式之后把c2[ ]拷贝给c1[ ],同时把c2[ ]清零
memset(c2,,sizeof(c2));
c1[]=;//指数为0的系数为1
for(int i=;i<=n;++i){//n个多项式
for(int j=;j<=n;++j)//指数最大不超过n,0~n
for(int k=;k+j<=n;k+=i)//当前第i个多项式的指数步长为i。现将多项式中指数为0~n的每一项去乘以当前第i项多项式中的每一项,得到的指数为j+k,由于第i个多项式中每一项前面的系数都为1,因此得到指数为j+k的系数为在原来的基础上加上指数为j的系数C1[j]即可
c2[j+k]+=c1[j];
for(int j=;j<=n;++j) //把c2[j]即指数为j(j∈[0,n])的每一项系数赋给c1[j],并且把c2[ ]清零
c1[j]=c2[j],c2[j]=;
}
printf("%d\n",c1[n]);//x^n的系数就是整数n的划分方案数。
}
return ;
}

题解报告:hdu 1028 Ignatius and the Princess III(母函数or计数DP)的更多相关文章

  1. hdu 1028 Ignatius and the Princess III 母函数

    Ignatius and the Princess III Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K ...

  2. HDU 1028 Ignatius and the Princess III (递归,dp)

    以下引用部分全都来自:http://blog.csdn.net/ice_crazy/article/details/7478802  Ice—Crazy的专栏 分析: HDU 1028 摘: 本题的意 ...

  3. hdu 1028 Ignatius and the Princess III 简单dp

    题目链接:hdu 1028 Ignatius and the Princess III 题意:对于给定的n,问有多少种组成方式 思路:dp[i][j],i表示要求的数,j表示组成i的最大值,最后答案是 ...

  4. HDU 1028 Ignatius and the Princess III 整数的划分问题(打表或者记忆化搜索)

    传送门: http://acm.hdu.edu.cn/showproblem.php?pid=1028 Ignatius and the Princess III Time Limit: 2000/1 ...

  5. hdu 1028 Ignatius and the Princess III(DP)

    Ignatius and the Princess III Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K ...

  6. HDU 1028 Ignatius and the Princess III (母函数或者dp,找规律,)

    Ignatius and the Princess III Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K ...

  7. hdu 1028 Ignatius and the Princess III (n的划分)

    Ignatius and the Princess III Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K ...

  8. HDU 1028 Ignatius and the Princess III (生成函数/母函数)

    题目链接:HDU 1028 Problem Description "Well, it seems the first problem is too easy. I will let you ...

  9. HDU 1028 Ignatius and the Princess III (动态规划)

    题目链接:HDU 1028 Problem Description "Well, it seems the first problem is too easy. I will let you ...

随机推荐

  1. Import CAD geometry in BladeModeler, turbogrid

    Table of Contents 1. Import CAD geometry in BladeModeler, turbogrid 1 Import CAD geometry in BladeMo ...

  2. 【BZOJ 1013】球形空间产生器sphere(高斯消元)

    球形空间产生器sphere HYSBZ - 1013 (高斯消元) 原题地址 题意 给出n维的球上的n个点,问原球体球心. 提示 n维球体上两点距离公式\(dist = \sqrt{ (a1-b1)^ ...

  3. PAT 1141 PAT Ranking of Institutions

    After each PAT, the PAT Center will announce the ranking of institutions based on their students' pe ...

  4. PAT 1125 Chain the Ropes

    Given some segments of rope, you are supposed to chain them into one rope. Each time you may only fo ...

  5. String类的判断功能

    /* * Object:是类层级结构中的根类,所有的类都直接或间接的继承自该类. * 如果一个方法的形式参数是Object,那么这里我们就可以传递它的任意的子类对象. * * String类的判断功能 ...

  6. HDU 3308 (线段树区间合并)

    http://acm.hdu.edu.cn/showproblem.php?pid=3308 题意: 两个操作  : 1 修改 单点  a 处的值. 2 求出 区间[a,b]内的最长上升子序列. 做法 ...

  7. Linux RAR 解压缩

    1.下载 http://www.rarlab.com/download.htm 2.安装 tar zxvf rarlinux-3.8.0.tar.gz cd rar make make install ...

  8. [bzoj 1042][HAOI2008]硬币购物(用容斥原理弄背包)

    题目:http://www.lydsy.com:808/JudgeOnline/problem.php?id=1042 分析: 解法很巧妙,用f[i]表示四种硬币A.B.C.D的数量不考虑的情况下弄成 ...

  9. mybatis中的map.xml文件中sql语句需要分号吗?

    mybatis中的map.xml文件中sql语句需要分号吗? :你是说sql介绍的分号吗?不需要的

  10. Android实现微博分享及其注意事项

    在前面我写了两篇关于QQ和微信的分享(http://blog.csdn.net/dawanganban/article/details/42015249)(http://blog.csdn.net/d ...