hdu 1028 整数的划分问题

Posted fengzeng666

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了hdu 1028 整数的划分问题相关的知识,希望对你有一定的参考价值。

"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

10 
20

Sample Output

42 
627
 
 

思路

技术图片

技术图片
假设partition(n,m):正整数n的划分中加数小于等于m的所有划分数。
一般情况下,有:
partion(n, m) = partition(n, m-1) + partition(n-m, m);
 
例如:
比如partition(7,4) = partition(7,3)+partition(3,4),为什么会加上partition(3,4)呢?
4+3, 4+2+1,4+1+1+1这一行的总个数就是partition(3,4),
相当于把最前面固定的4去掉,剩余项的和等于7-4=3的总个数,但同时剩余项的加数要小于4,因为这些数排在删掉的4的后面。
 
特殊情况(递归终止条件):
(1)partition(n,m) = partition(n,n-1) + 1
         n<=m时,有 partition(n,m) = partition(n,n-1) + 1,因为n的划分不能有大于n的加数
(2)partition(1,n) = 1
         n = 1时,不管m有多大,整数1都只有1个划分
(3)partition(n,1) = 1
         对任意整数n,加数小于等于1的划分只有1个,即1+1+....+1
 
使用记忆化搜索优化递归次数,得到如下代码:
 1 #include <iostream>
 2 #include <vector>
 3 #include <stdio.h>
 4 #include <string>
 5 
 6 using namespace std;
 7 
 8 #define MAXN 150
 9 
10 vector<vector<int>> memo;
11 
12 int partition(int n, int m)
13 {
14     if(n < 1 || m < 1)
15         return 0;
16     
17     if(n == 1 || m == 1)
18         return 1;
19     
20     if(memo[n][m] != -1)
21         return memo[n][m];
22         
23     if(n <= m)
24         memo[n][m] = 1+partition(n,n-1);
25     else
26         memo[n][m] = partition(n,m-1) + partition(n-m,m);
27     
28     return memo[n][m];
29     
30 } 
31 
32 int main()
33 {
34     int n;
35     while(scanf("%d", &n) != EOF)
36     {
37         memo = vector<vector<int>>(MAXN, vector<int>(MAXN, -1));
38         printf("%d
", partition(n,n));
39     }
40     
41     return 0;
42 }

 


 
 

以上是关于hdu 1028 整数的划分问题的主要内容,如果未能解决你的问题,请参考以下文章

hdu1028 划分数

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

hdu 1028 Ignatius and the Princess III —— 整数划分(生成函数)

hdu 1028题解

hdu,1028,整数拆分的理解

HDU 1028 Ignatius and the Princess III dp