动态规划解整数划分

来源:互联网 发布:金蝶eas数据字典 编辑:程序博客网 时间:2024/04/30 15:02

算法思路:

n = n1 + n2 + n3 + n4 + .... + nk
(n1>=n2>=n3>=....>=nk),从大到小排列后,可以避免陷入数值大小排序顺序的困境中。这样,在下面的过程,我们可以并不关心数值大小的排列,只关心组合方案数。

状态表示:将最大加数n1不大于m的划分个数记作q(n,m)
状态转移:
(1) q(n,1) = 1,n>=1
当最大加数n1不大于1时,任何正整数n只有一种划分方式,即 n = 1+1+1+..+1 (n个1相加)。
(2)q(n,m) = q(n,n),m>n
最大加数n1实际上不能大于n。因此q(1,m)=1。
(3)q(n,n) = 1+q(n,n-1)
正整数n的划分由n1=n的划分和n1<=n-1的划分组成。
(4)q(n,m) = q(n,m-1) + q(n-m,m),n>m>1
正整数n的最大加数n1不大于m的划分由n1=m的划分和n1<=m-1的划分组成。


另一个思路有点相似的问题:

1-100中,   
求:5个不同数的和小于100的不重复组合的个数.   


设立一个数组A[5][100][100]
A[i][j][k]表示用i个[j, 100]之间的不同的数,最小数为j且和小于k的组合有多少种
//假设数组下标从1开始
则有
A[i][j][k] = SIGMA{ A[i-1][m][k-j] } m属于[j+1, k]


e.g.
A[5][1][100]
表示所求组合中,最小的那个数为1的情况
那么其余四个数中最小的至少是2,并且那四个数和小于99
所以A[5][1][100] = A[4][2][99] + A[4][3][99] + ...