`
haierboos
  • 浏览: 438218 次
文章分类
社区版块
存档分类
最新评论

整数划分算法原理与实现

 
阅读更多

本文为原创,如需转载,请注明作者和出处,谢谢!

整数划分问题是将一个正整数n拆成一组数连加并等于n的形式,且这组数中的最大加数不大于n。
如6的整数划分为

6
5 + 1
4 + 2, 4 + 1 + 1
3 + 3, 3 + 2 + 1, 3 + 1 + 1 + 1
2 + 2 + 2, 2 + 2 + 1 + 1, 2 + 1 + 1 + 1 + 1
1 + 1 + 1 + 1 + 1 + 1

共11种。下面介绍一种通过递归方法得到一个正整数的划分数。

递归函数的声明为 int split(int n, int m);其中n为要划分的正整数,m是划分中的最大加数(当m > n时,最大加数为n),
1 当n = 1或m = 1时,split的值为1,可根据上例看出,只有一个划分1 或 1 + 1 + 1 + 1 + 1 + 1
可用程序表示为if(n == 1 || m == 1) return 1;

2 下面看一看m 和 n的关系。它们有三种关系
(1) m > n
在整数划分中实际上最大加数不能大于n,因此在这种情况可以等价为split(n, n);
可用程序表示为if(m > n) return split(n, n);
(2) m = n
这种情况可用递归表示为split(n, m - 1) + 1,从以上例子中可以看出,就是最大加
数为6和小于6的划分之和
用程序表示为if(m == n) return (split(n, m - 1) + 1);
(3) m < n
这是最一般的情况,在划分的大多数时都是这种情况。
从上例可以看出,设m = 4,那split(6, 4)的值是最大加数小于4划分数和整数2的划分数的和。
因此,split(n, m)可表示为split(n, m - 1) + split(n - m, m)

根据以上描述,可得源程序如下:

<!--<br /> <br /> Code highlighting produced by Actipro CodeHighlighter (freeware)<br /> http://www.CodeHighlighter.com/<br /> <br /> -->#include<stdio.h>

intsplit(intn,intm)
{
if(n<1||m<1)return0;
if(n==1||m==1)return1;
if(n<m)returnsplit(n,n);
if(n==m)return(split(n,m-1)+1);
if(n>m)return(split(n,m-1)+split((n-m),m));
}

intmain()
{
printf(
"12的划分数:%d",split(12,12));
return0;
}

将正整数划分成连续的正整数之和

如15可以划分成4种连续整数相加的形式:


15


7 8


4 5 6


1 2 3 4 5



首先考虑一般的形式,设n为被划分的正整数,x为划分后最小的整数,如果n有一种划分,那么


结果就是x,如果有两种划分,就是x和x x + 1, 如果有m种划分,就是 x 、x x + 1 、 x x + 1 x + 2 、... 、x x + 1 x + 2 ... x + m - 1


将每一个结果相加得到一个公式(i * x + i * (i - 1) / 2) = n,i为当前划分后相加的正整数个数。


满足条件的划分就是使x为正整数的所有情况。


如上例,当i = 1时,即划分成一个正整数时,x = 15, 当i = 2时, x = 7。


当x = 3时,x = 4, 当x = 4时,4/9,不是正整数,因此,15不可能划分成4个正整数相加。


当x = 5时,x = 1。



这里还有一个问题,这个i的最大值是多少?不过有一点可以肯定,它一定比n小。我们可以做一个假设,


假设n可以拆成最小值为1的划分,如上例中的1 2 3 4 5。这是n的最大数目的划分。如果不满足这个假设,


那么 i 一定比这个划分中的正整数个数小。因此可以得到这样一个公式i * (i + 1) / 2 <= n,即当i满足


这个公式时n才可能被划分。



综合上述,源程序如下


<!--<br /> <br /> Code highlighting produced by Actipro CodeHighlighter (freeware)<br /> http://www.CodeHighlighter.com/<br /> <br /> -->intsplit1(intn)
{
inti,j,m=0,x,t1,t2;
//在这里i+1之所以变为i-1,是因为i*(i-1)/2这个式子在下面多次用到,
//为了避免重复计算,因此将这个值计算完后保存在t1中。并且将<=号变为了<号。
for(i=1;(t1=i*(i-1)/2)<n;i++)
{
t2
=(n-t1);
x
=t2/i;
if(x<=0)break;
if((n-t1)%i==0)
{
printf(
"%d",x);
for(j=1;j<i;j++)
printf(
"%d",x+j);
printf(
"/n");
m
++;
}
}
returnm;
}


国内最棒的Google Android技术社区(eoeandroid),欢迎访问!

《银河系列原创教程》发布
分享到:
评论

相关推荐

    算法设计与分析期末论文

    探究目的 分析并掌握“整数划分”问题的递归算法。 调试整数划分的代码,并分析原理。 在课本代码的基础上探究实现整数划分的具体输出。

    实验一:递归函数的设计与实现

    实验目的:掌握递归函数的设计与实现方法 ...实验步骤:编写程序实现教材P12例2-5 整数划分问题 问题描述:整数划分问题是将一个正整数n拆成一组数连加并等于n的形式,且这组数中的最大加数不大于n。

    算法导论(part2)

    ·快速排序(第7.1节)中用到的划分方法与期望线性时间顺序统计算法(expected linear-time order-statistic algorithm,第9.2节)有所变化。现在,我们采用了Lomuto提出的方法,并将该方法与指示器随机变量一起使用,...

    算法导论(part1)

    ·快速排序(第7.1节)中用到的划分方法与期望线性时间顺序统计算法(expected linear-time order-statistic algorithm,第9.2节)有所变化。现在,我们采用了Lomuto提出的方法,并将该方法与指示器随机变量一起使用,...

    精华游戏算法整理(经典)

    经过努力,终于完成了文档,也明白的A*算法的原理。毫 无疑问,作者用形象的描述,简洁诙谐的语言由浅入深的讲述了这一神奇的算法,相信每个读过的人都会对此有所认识(如果没有,那就是偶的翻译太差了-- b)。 原文...

    IOI国家集训队论文集1999-2019

    周咏基 -《论随机化算法的原理与设计》 ## 2000 陈 彧 《信息学竞赛中的思维方法》 方 奇 《动态规划》 高寒蕊 -《递推关系的建立及在信息学竞赛中的应用》 郭 一 -《数学模型及其在信息学竞赛中的应用》 ...

    MD5加密算法(Java语言描述)

     对MD5算法简要的叙述可以为:MD5以512位分组来处理输入的信息,且每一分组又被划分为16个32位子分组,经过了一系列的处理后,算法的输出由四个32位分组组成,将这四个32位分组级联后将生成一个128位散列值。...

    2005-2009软件设计师历年真题

     • 算法与数据结构的关系、算法效率、算法设计、算法描述(流程图、伪代码、决策表)、算法的复杂性  2.计算机系统知识  2.1 硬件知识  2.1.1 计算机系统的组成、体系结构分类及特性  • CPU和存储器的组成、...

    超级有影响力霸气的Java面试题大全文档

    接口的实现与子类相似,除了该实现类不能从接口定义中继承行为。当类实现特殊接口时,它定义(即将程序体给予)所有这种接口的方法。然后,它可以在实现了该接口的类的任何对象上调用接口的方法。由于有抽象类,它...

    java 面试题 总结

    接口的实现与子类相似,除了该实现类不能从接口定义中继承行为。当类实现特殊接口时,它定义(即将程序体给予)所有这种接口的方法。然后,它可以在实现了该接口的类的任何对象上调用接口的方法。由于有抽象类,它...

    计算机二级公共基础知识

    性质4:具有n个结点的二叉树,其深度至少为[log2n]+1,其中[log2n]表示取log2n的整数部分。 3. 满二叉树与完全二叉树 满二叉树是指这样的一种二叉树:除最后一层外,每一层上的所有结点都有两个子结点。在满二叉树中...

    硬件工程师培训教程(二).doc

    一个典型的操作集包括 与内部数据类型相关的基本算术指令(即实数和整数加法、减法、乘法和除法等)、测试 数据项性质(如是否为零,是正数或负数等)的指令 、对数据项的某一部分进行存取和修 改 (如在一个字中存取一...

    硬件工程师培训教程000006).doc

    一个典 型的操作集包括与内部数据类型相关的基本算术指令(即实数和整数加法、减法、乘法和 除法等)、测试数据项性质(如是否为零,是正数或负数等)的指令 、对数据项的某一部 分进行存取和修改 (如在一个字中存取一...

    动态规划 ppt演示

    下面的算法LCS(b,X,i,j)实现根据b的内容打印出Xi与Yj的最长公共子序列。通过算法的调用LCS(b,X,length[X],length[Y]),便可打印出序列X和Y的最长公共子序列。 Procedure LCS(b,X,i,j);beginif i=0 or j=0 then ...

    ACM程序设计培训教程

    被毁坏的玉米地 ACM程序设计培训教程 经典数据结构与算法……………………………………………………………1  1.1 线性表………………………………………………………………………………1  1.1.1 线性表的顺序存储...

    oracle学习文档 笔记 全面 深刻 详细 通俗易懂 doc word格式 清晰 连接字符串

    从就业与择业的角度来讲,计算机相关专业的大学生从事oracle方面的技术是职业发展中的最佳选择。 其一、就业面广:全球前100强企业99家都在使用ORACLE相关技术,中国政府机构,大中型企事业单位都能有ORACLE技术的...

    ZendFramework中文文档

    4.2. 缓存原理 4.2.1. Zend_Cache 工厂方法 4.2.2. 标记纪录 4.2.3. 缓存清理 4.3. Zend_Cache前端 4.3.1. Zend_Cache_Core 4.3.1.1. 简介 4.3.1.2. 可用选项 4.3.1.3. 例子 4.3.2. Zend_Cache_Frontend_...

Global site tag (gtag.js) - Google Analytics