第3章 递推算法(C++版)
C++函数、递推、递归ppt课件
i = 7 s1 = 2 * (s2 + 1) ; s2 = s1 ;
// S(7) = 2 * (S(8) + 1) // s2 = s1 = S(7)
i = 6 s1 = 2 * (s2 + 1) ; s2 = s1 ;
// S(6) = 2 * (S(7) + 1) // s2 = s1 = S(6)
看一个简单的例子:
1 4
第九讲——函数、递推、递归
递归
有 5 个人坐在一起,问第 5 个人多少岁? 他说比第 4 个人 大两岁。问第 4 个人岁数,他说比第 3 个人大两岁。问第 3 个人,又说比第 2 个人大两岁。问第 2 个人,说比第 1 个人 大两岁。最后问第 1 个人,他说是 10 岁。请问第 5 个人多 大?
3
第九讲——函数、递推、递归
解题思路:
假设用 S(i) 表示第 i 天没吃之前的桃子数目;
则
S(1) 即为第 1 天所摘的桃子数; S(2) = S(1) * 1/2 – 1 第 2 天没吃之前的桃子数
S(3) = S(2) * 1/2 - 1 第 3 天没吃之前的桃子数
…
…
S(9) = S(8) * 1/2 - 1 第 9 天没吃之前的桃子数
= age(2) + 2 + 2 + 2 // c = age(2) + 2
= age(1) + 2 + 2 + 2 + 2;// c = 10;
2 2
计算年龄程序
第九讲——函数、递推、递归
2 3
第九讲——函数、递推、递归
递归算例(2)
用递归方法计算 n! 算法思路:
递推算法(C++版)
int main()
{
int n,i,j,a[101];
cout<<"input n:";
//输入骨牌数
cin>>n;
a[1]=1;a[2]=2;
cout<<"x[1]="<<a[1]<<endl;
cout<<"x[2]="<<a[2]<<endl;
for (i=3;i<=n;i++)
//递推过程
{
int n,m; cin>>m>>n; int m1=m,n1=n,s1=m*n; while (m1!=0&&n1!=0) {
m1--;n1--; s1+=m1*n1; } int s2=((m+1)*(n+1)*m*n)/4-s1; cout<<s1<<" "<<s2<<endl; }
//计算正方形的个数s1 // 计算长方形的个数s2
其实,本题稍加分析就能发现,要到达棋盘上的一个点,只能从左边过 来(我们称之为左点)或是从上面过来(我们称之为上点),所以根据加 法原理,到达某一点的路径数目,就等于到达其相邻的上点和左点的路径 数目之和,因此我们可以使用逐列(或逐行)递推的方法来求出从起点到 终点的路径数目。障碍点(马的控制点)也完全适用,只要将到达该点的 路径数目设置为0即可。
个正方形、多少个长方形(不包括正方形)。
例如:当 N=2, M=3时:
正方形的个数有8个:即边长为1的正方形有6个;边长为2的正方形有2个。
04.递推算法(C++版包括习题参考答案)
s 1=
(n i ) * (m i )
2.长方形和正方形的个数之和s 宽为1的长方形和正方形有m个,宽为2的长方形和正方形有 m-1个,┉┉,宽为m的长方形和正方形有1个; 长为1的长方形和正方形有n个,长为2的长方形和正方形有n1个,┉┉,长为n的长方形和正方形有1个; 根据乘法原理
【参考程序】 #include<iostream> using namespace std; int main() { int f[1001][2],n,i,x; cin>>n; f[1][1]=1;f[1][0]=9; for(i=2;i<=n;i++) { x=f[1][0]; if(i==n)x--; f[i][0]=(f[i-1][0]*x+f[i-1][1])%12345; f[i][1]=(f[i-1][1]*x+f[i-1][0])%12345; } cout<<f[n][0]; return 0; }
下面是输入n,输出x1~xn的c++程序: #include<iostream> using namespace std; int main() { int n,i,j,a[101]; cout<<"input n:"; //输入骨牌数 cin>>n; a[1]=1;a[2]=2; cout<<"x[1]="<<a[1]<<endl; cout<<"x[2]="<<a[2]<<endl; for (i=3;i<=n;i++) //递推过程 { a[i]=a[i-1]+a[i-2]; cout<<"x["<<i<<"]="<<a[i]<<endl; } } 下面是运行程序输入 n=30,输出的结果: input n: 30 x[1]=1 x[2]=2 x[3]=3 ........ x[29]=832040 x[30]=1346269
计算机常用算法与程序设计第3章 递推
3.3 裴波那契序列与卢卡斯序列
案例提出: 裴波那契数列定义为:
F1 F2 1
Fn Fn 1 Fn 2
(n 2)
卢卡斯数列定义为:
L1 1, L2 3 Ln Ln 1 Ln 2 ( n 2)
试求解裴波那契数列或卢卡斯数列的第n项与前n
项之和(n从键盘输入)。
1. 递推设计要点
(1)应用试商法产生素数判别函数p(k):若k为素数, p(k)返回1;否则,p(k)返回0。 (2)根据超级素数的定义, n位超级素数去掉高位数字 后是n-1位超级素数。一般地k(k=2,3,…,n)位超级素数去 掉高位数字后是k-1位超级素数。 (3)已求得g个k-1位超级素数a[i](i=1,2,…,g)时,在a[i] 的高位加上一个数字j(j=1,2,…,9),得到9g个k位候选数 f=j*e[k]+a[i],(e[k]=10k-1),只要对这9g个k位候选数检测即 可。这就是从k-1递推到k的递推关系。 (4)注意到超级n(n>1)位素数的个位数字必然是3 或7,则得递推的初始(边界)条件:a[1]=3,a[2]=7,g=2;
(3)较复杂的递推问题需设置多重循环递推。
( 4 )ຫໍສະໝຸດ 多关系分级递推算法当递推关系包含两个或两个以上关系式时,通常应用 多关系分级递推算法求解。 f(1:i-1)=<初始值>; // 赋初始值 for(k=i;k<=n;k++) { if(<条件1>) f(k)=<递推关系式1>; // 根据关系1递推 …… if(<条件m>) f(k)=<递推关系式m>; // 根据关系m递推 } print(f(n)); // 输出n规模的解f(n)
递推法在C语言中的简单应用
10
确定约瑟夫问题的基线情况:
想确定约瑟夫问题的基线情况,只需要证明递推式对于 人数n小于出列编号m的情况依然满足即可。 分界处 n-k+1 m=c*n+k n-k n n-k-1 n-1 n-k-2 n-2 分界处 k+1 k k-1 1 n-1 1 n-k+2 2 将图分为两部分,由于 n-k+3 两部分编号均递增且增 3 值为1,所以只需证明两 4 n-k+4 部分开头满足递推 (1+c*n+k)%n=k+1成立 (n-k+1+c*n+k)%n=1成立
即a(1)为基线情况
11
用例:有n个标牌成圆排列,编号1,2,3…n,用4种不同的颜色染色, 要求相邻两标牌颜色不同,求有多少种染色方法? 建立递推:a n = 2 * a n – 1 + 3 * a n – 2 n个标牌染色方法数为a(n),去掉n号标牌,n-1号标牌有两种情况 (与1颜色相同或不同); 若与1号颜色相同,n-2号与1号不同,n号标牌有3种染色方式, 去掉n-1号,转化为n-2个标牌的情景,所以方法数为3*a(n数=两个数的乘积 (2)3000以上没有数满足类似水仙花数的性质 可见,数学技巧的应用可以起到锦上添花的作用,但是…… 数学只能解决一部分问题
数学只是一门工具学科,所以我们要应用数学而不是依赖数学。 数学绝对可以帮助优化程序,学好编程,但是不会让你学会编 程。学好是建立在学会的基础上。所以,希望同学们在有意积 累数学知识的同时,更加重视C语言基本课程的学习。
7
用a(i) 代替 a i,补充定义a(0)=0; 构建递推式如下: a(n) = a(0) * a(n-1) + a(1) * a(n-2) + … + a(k-1) * a(n-k) + … +a(n-2) * a(1) + a(n-1) * a(0) 且 a(0) = 1 , a(1) = 1
第三章 递推算法
第三章 递推算法【上机练习】1、走楼梯(stairs)楼梯有N级台阶,上楼可以一步上一阶,也可以一步上二阶。
编一递归程序,计算共有多少种不同走法?【输入样例】3【输出样例】32、兔子繁殖(rabbit)有一种兔子,出生后一个月就可以长大,然后再过一个月一对长大的兔子就可以生育一对小兔子且以后每个月都能生育一对。
现在,我们有一对刚出生的这种兔子,那么,n个月过后,我们会有多少对兔子呢?假设所有的兔子都不会死亡。
【输入格式】输入文件仅一行,包含一个自然数n。
【输出格式】输出文件仅一行,包含一个自然数,即n个月后兔子的对数。
【输入样例】5【输出样例】53、平面分割(surface)同一平面内有n(n≤500)条直线,已知其中p(p≥2)条直线相交于同一点,则这n条直线最多能将平面分割成多少个不同的区域?【输入格式】两个整数n(n≤500)和p(2≤p≤n)。
【输出格式】一个正整数,代表最多分割成的区域数目。
【输入样例】12 5【输出样例】734、骨牌铺法(domino)有1×n的一个长方形,用一个1×1、1×2和1×3的骨牌铺满方格。
例如当n=3时为1×3的方格。
此时用1×1、1×2和1×3的骨牌铺满方格,共有四种铺法。
如下图:【输入样例】3【输出样例】45、蜜蜂路线(bee)【问题描述】一只蜜蜂在下图所示的数字蜂房上爬动,已知它只能从标号小的蜂房爬到标号大的相邻蜂房,现在问你:蜜蜂从蜂房M开始爬到蜂房N,M<N,有多少种爬行路线?【输入格式】 输入M,N的值。
【输出格式】 爬行有多少种路线。
【输入样例】1 14【输出样例】3776、极值问题(acme)【问题描述】已知m、n为整数,且满足下列两个条件:① m、n∈{1,2,…,k},即1≤m,n≤k②(n2-m*n-m2)2=1你的任务是:编程输入正整数k(1≤k≤109),求一组满足上述两个条件的m、n,并且使m2+n2的值最大。
04.递推算法(C++版包括习题参考答案)
【例6】过河卒(Noip2002) 【问题描述】 棋盘上A点有一个过河卒,需要走到目标B点。卒行走的规则:可以向 下、或者向右。同时在棋盘上的任一点有一个对方的马(如C点),该马 所在的点和所有跳跃一步可达的点称为对方马的控制点,如图3-1中的C点 和P1,„„,P8,卒不能通过对方马的控制点。棋盘用坐标表示,A点 (0,0)、B点(n, m) (n,m为不超过20的整数),同样马的位置坐标是需要给 出的,C≠A且C≠B。现在要求你计算出卒从A点能够到达B点的路径的条数。
min{m , n}1 i 0
s 1=
(n i ) * (m i )
2.长方形和正方形的个数之和s 宽为1的长方形和正方形有m个,宽为2的长方形和正方形有 m-1个,┉┉,宽为m的长方形和正方形有1个; 长为1的长方形和正方形有n个,长为2的长方形和正方形有n1个,┉┉,长为n的长方形和正方形有1个; 根据乘法原理
【例3】棋盘格数
设有一个N*M方格的棋盘( l≤ N≤100,1≤M≤100)。求出该棋盘中包含有多少 个正方形、多少个长方形(不包括正方形)。 例如:当 N=2, M=3时: 正方形的个数有8个:即边长为1的正方形有6个;边长为2的正方形有2个。 长方形的个数有10个:即2*1的长方形有4个:1*2的长方形有3个:3*1的长 方形有2个:3*2的长方形有1个: 程序要求:输入:N,M 输出:正方形的个数与长方形的个数 如上例:输入:2 3 输出:8 10 【算法分析】 1.计算正方形的个数s1 边长为1的正方形个数为n*m 边长为2的正方形个数为(n-1)*(m-1) 边长为3的正方形个数为(n-2)*(m-2) ………… 边长为min{n,m}的正方形个数为(m-min{n,m}+1)*(n-min{n,m}+1) 根据加法原理得出
信息学奥赛系列课程(三阶段)-2019_02_21_第3版
信息学奥赛NOIP系列课程(三阶段)第一阶段C++语言及数据结构与算法基础课本:1、信息学奥赛一本通+训练指导教程C++版第五版--2017年出版(两本)第1部分C++语言(50课时)适于:零基础的初中或高中的学生,当然有C语言或scratch、Python语言基础更好授课:相关内容讲授+实例+题目现堂训练(每次课2-3题,题目较大可能是1题)第1章C++语言入门(2-3课时)第2章顺序结构程序设计(6课时)第3章程序控制结构(3课时)NOIP2017复赛普及组第1题成绩https:///problem-12334.htmlNOIP2018复赛普及组第1题标题统计方法一https:///problem-12393.htmlNOIP1996普及组第1题https:///WDAJSNHC/article/details/83513564https:///yuyanggo/article/details/47311665第4章循环结构(5课时)NOIP2018复赛普及组第1题标题统计方法二https:///problem-12393.htmlNOIP2016复赛普及组第1题买铅笔https:///problem-12121.htmlNOIP2015复赛普及组第1题金币/ch0105/45/NOIP2002复赛普及组第1题级数求和/ch0105/27/NOIP2013复赛普及组第1题计数问题https:///problem-11005.html?tdsourcetag=s_pcqq_aiomsgNOIP2012复赛普及组第1题质因数分解/ch0105/43/NOIP2011复赛普及组第1题数字反转/ch0105/29/NOIP2010复赛普及组第1题数字统计https:///problem-10012.htmlNOIP1999普及组第1题Cantor表/ch0201/8760/https:///problemnew/show/P1014NOIP1997普及组第1题棋盘问题https:///problemnew/show/P1548NOIP1995普及组复赛第1题https:///secret_zz/article/details/76862335https:///WDAJSNHC/article/details/83513896NOIP1997普及组第2题数字三角形https:///ber_bai/article/details/76722379第5章数组(9-10课时)NOIP2014复赛普及组第1题珠心算测验https:///problem-12091.htmlNOIP2009复赛普及组第1题多项式输出/ch0113/39/NOIP2006复赛普及组第1题明明的随机数/ch0110/09/NOIP2005复赛普及组第1题陶陶摘苹果/ch0106/02/NOIP2004复赛普及组第1题不高兴的津津/ch0109/03/NOIP2003年普及组第1题乒乓球/ch0113/37/NOIP1998年普及组第1题三连击(枚举)https:///problemnew/show/P1008NOIP1995普及组复赛第2题方阵填数https:///WDAJSNHC/article/details/79381876NOIP1996普及组第2题格子问题https:///WDAJSNHC/article/details/79381843?utm_source=blogxgwz5NOIP2016复赛普及组第2题回文日期https:///problem-12122.htmlhttps:///problemnew/show/P2010NOIP2015普及组第2题P2670扫雷游戏/ch0108/14/https:///problemnew/show/P2670https:///problem-12105.htmlNOIP2012普及组第2题_P1076寻宝/ch0112/06/https:///problemnew/show/P1076第6章函数(5课时)NOIP2008复赛普及组第1题ISBN号码/ch0107/29/NOIP2000提高组第1题P1017进制转换https:///problemnew/show/P1017NOIP2000普及组第1题计算器的改良https:///problemnew/show/P1022https:///yuyanggo/article/details/47856785https:///u012773338/article/details/41749421NOIP2018普及组第2题龙虎斗https:///problemnew/show/P5016https:///problem-12394.html机器翻译【1.12编程基础之函数与过程抽象07】Noip2010提高组第1题/ch0112/07/Vigenère密码【1.12编程基础之函数与过程抽象08】Noip2012提高组第1题/ch0112/08/笨小猴【1.9编程基础之顺序查找06】NOIP2008提高组第1题/ch0109/06/第7章文件和结构体(5课时)NOIP2011复赛提高组第1题铺地毯/ch0109/14/NOIp2008提高组第2题火柴棒等式https:///problemnew/show/P1149https:///Mr_Doublerun/article/details/52589778第8章指针及其应用(8课时)第9章C++实用技巧与模版库(5课时)NOIP2007复赛普及组第1题奖学金/ch0110/04/NOIP2017复赛普及组第2题图书管理员(STL、排序)https:///problem-12335.htmlhttps:///problemnew/show/P3955NOIP1999普及组第2题回文数https:///problemnew/show/P1015***模拟NOIP2017年提高组第2题时间复杂度(模拟)https:///problem-12333.htmlhttps:///problemnew/show/P3952NOIP2011普及组第3题P1309瑞士轮(模拟、快拍、归并排序)/ch0401/4363/https:///problemnew/show/P1309NOIP2018复赛普及组第3题摆渡车(模拟)https:///problem-12395.htmlhttps:///problemnew/show/P5017NOIP2016普及组第3题海港(port)--枚举https:///problemnew/show/P2058NOIP2006年提高组第3题P1065作业调度方案(模拟)https:///problemnew/show/P1065NOIP2013提高组第4题P1969积木大赛(模拟贪心)https:///problem-12071.htmlhttps:///problemnew/show/P1969NOIP2014提高组第4题P2038无线网络发射器选址(模拟)https:///problemnew/show/P2038第2部分NOIP基础算法(39课时)第1章高精度计算(2-3课时)【例1.6】回文数(Noip1999):8088/problem_show.php?pid=1309NOIP2003普及组第4题P1045麦森数(分治、高精度运算)https:///problemnew/show/P1045NOIP2005普及组第4题P1050循环(高精度运算、数论、快速幂) https:///problemnew/show/P1050第2章数据排序(3课时)NOIP2014复赛普及组第1题珠心算测验https:///problem-12091.html第3章递推算法(2-3课时)1314:【例3.6】过河卒(Noip2002):8088/problem_show.php?pid=1314NOIP2011普及组第4题P1310表达式的值(栈、表达式计算、递推) https:///problemnew/show/P1310NOIP2011提高组第6题P1315观光公交(递推分析、贪心)https:///problemnew/show/P1315第4章递归算法(2-3课时)【例4.6】数的计数(Noip2001普及组第1题):8088/problem_show.php?pid=1316第5章搜索与回溯算法(2-3课时)NOIP2015day1T3_斗地主P2668斗地主https:///problemnew/show/P2668NOIP2017年普及组第3题棋盘https:///problemnew/show/P3956https:///problem-12336.htmlNOIP2015年提高组第2题P2661信息传递(Tarjen bfs/dfs(图论))https:///problem-12107.htmlhttps:///problemnew/show/P2661NOIP2016年提高组第2题天天爱跑步(Lca/dfs(图论)树结构最近公共祖先)https:///problem-12208.htmlhttps:///problemnew/show/P1600NOIP2000普及组第4题P1019单词接龙(深搜)https:///problemnew/show/P1019NOIP2000年提高组第3题单词接龙(DFS,字符串,模拟)https:///problemnew/show/P1019NOIP2014普及组第4题P2258子矩阵(搜索或dp)https:///problemnew/show/P2258NOIP2018年提高组第3题P5021赛道修建(搜索深度优先搜索)https:///problem-12392.htmlhttps:///problemnew/show/P5021第6章贪心算法(3课时)删数问题(NOIP1994)P1106删数问题https:///problemnew/show/P1106:8088/problem_show.php?pid=1321NOIP2010复赛普及组第2题接水问题/ch0109/15/NOIP1999年提高组第1题导弹拦截https:///problemnew/show/P1020https:///huashanqingzhu/p/6728652.html https:///qq_33927580/article/details/51853345 https:///Darost/article/details/52086240https:///yuyanggo/article/details/48739029NOIP2002提高组第1题均分纸牌P1031均分纸牌https:///problemnew/show/P1031NOIP2007普及组第2题_P1094纪念品分组https:///problem-12007.htmlhttps:///problemnew/show/P1094NOIP2008普及组第2题_P1056排座椅https:///problem-12008.htmlhttps:///problemnew/show/P1056NOIP2012年提高组第2题国王游戏(贪心、排序后列出)https:///problemnew/show/P1080NOIP2013年提高组第2题P1966火柴排队(逆序对、贪心、排序) https:///problem-12083.htmlhttps:///problemnew/show/P1966NOIP2010普及组第4题P1199三国游戏(贪心)https:///problemnew/show/P1199第7章分治算法(3课时)NOIP2001提高组第1题P1024一元三次方程求解/ch0204/7891/https:///problemnew/show/P1024NOIP2011年提高组第2题P1311选择客栈(二分查找)https:///problemnew/show/P1311NOIP2003普及组第4题P1045麦森数(分治、高精度运算)https:///problemnew/show/P1045第8章广度优先搜索算法(2-3课时)NOIP2002年提高组第2题P1032字串变换(BFS,字符串)https:///problemnew/show/P1032NOIP2013提高组第6题P1979华容道(广搜\最短路:图论)https:///problem-12212.htmlhttps:///problemnew/show/P1979第9章动态规划(15课时)第一节动态规划的基本模型1260:【例9.4】拦截导弹(NOIP1999):8088/problem_show.php?pid=1260NOIP2013普及组第3题P1982小朋友的数字https:///problemnew/show/P1982NOIP2003复赛普及组第2题_P1043数字游戏数字游戏(Game.cpp)https:///problemnew/show/P1043NOIP2006年提高组第2题P1064金明的预算方案(资源分配DP,构造) https:///problemnew/show/P1064NOIP2013普及组第3题P1982小朋友的数字(动态规划、子段和)https:///problemnew/show/P1982NOIP2007普及组第3题P1095守望者的逃离(动态规划或枚举)https:///problemnew/show/P1095NOIP2009普及组第4题P1070道路游戏(动态规划)https:///problemnew/show/P1070NOIP2004年提高组第3题P1091合唱队形(子序列DP)https:///problemnew/show/P1091第二节背包问题NOIP2018提高组第2题货币系统https:///problem-12391.htmlNOIP2006普及组第2题_P1060开心的金明题解https:///problemnew/show/P1060NOIP2005普及组第3题P1048采药(0/1背包)/ch0206/1775/https:///problem-12062.htmlhttps:///problemnew/show/P1048NOIP2001普及组第4题P1049装箱问题(0/1背包或枚举)https:///problemnew/show/P1049NOIP2014年提高组第3题P1941飞扬的小鸟(背包DP)https:///problem-12087.htmlhttps:///problemnew/show/P1941第三节动态规划经典题NOIP2000年提高组第2题P1018乘积最大(资源分配DP)https:///problemnew/show/P1018NOIP2000普及组第3题P1018乘积最大(划分动态规划)https:///problemnew/show/P1018NOIP2001年提高组第2题P1025数的划分(资源分配DP,多维状态DP)/ch0206/8787/https:///problemnew/show/P1025NOIP2001年提高组第3题统计单词个数(资源分配DP,字符串) https:///problemnew/show/P1026NOIP2005年提高组第2题P1052过河(子序列DP,贪心优化)https:///problemnew/show/P1052NOIP2010年提高组第2题P1541乌龟棋(动态规划优化)https:///problemnew/show/P1541NOIP2014年提高组第2题P1351联合权值(动态规划搜索图结构树形DP图的遍历遍历(图论),二次展开式)https:///problem-12086.htmlhttps:///problem-12210.htmlhttps:///problemnew/show/P1351NOIP2008普及组第3题P1057传球游戏(动态规划)https:///problemnew/show/P1057NOIP2012普及组第3题摆花(动态规划)https:///problem-12366.htmlhttps:///problemnew/show/P1077NOIP2002普及组第4题P1002过河卒(棋盘动态规划)https:///problemnew/show/P1002NOIP2008年提高组第3题P1006传纸条(多维状态DP动态规划图结构最短路网络流)https:///problem-12110.htmlhttps:///problemnew/show/P1006NOIP2000提高组第4题方格取数(多维状态DP)/ch0206/8786/https:///problem-12186.htmlhttps:///problemnew/show/P1004NOIP2002提高组第4题P1034矩形覆盖(动态规划/贪心/搜索剪枝) /ch0405/1793/https:///problemnew/show/P1034第3部分NOIP数据结构(19课时)第1章栈(3课时)NOIP2011普及组第4题P1310表达式的值(栈、表达式计算、递推) https:///problemnew/show/P1310第2章队列(3-5课时)NOIP2016普及组第3题海港(port)https:///problemnew/show/P2058第3章树(3课时)第一节树的概念第二节二叉树第三节堆及其应用NOIP2015普及组第4题P2672推销员(枚举、堆)https:///problemnew/show/P2672NOIP2001普及组第3题P1030求先序排列(树的遍历)https:///problemnew/show/P1030NOIP2004普及组第3题P1087FBI树(二叉树的遍历)https:///problemnew/show/P1087第4章图论算法(8课时)第一节基本概念第二节图的遍历第三节最短路径算法NOIP2002普及组第3题P1037产生数(最短路、高精度)https:///problemnew/show/P1037NOIP2012普及组第4题P1078文化之旅(搜索、最短路(图论)、动规) https:///problemnew/show/P1078NOIP2009年提高组第3题P1073最优贸易(最短路:图论)https:///problemnew/show/P1073NOIP2001提高组第4题P1027Car的旅行路线(最短路,实数处理)https:///problemnew/show/P1027NOIP2007提高组第4题P1099树网的核(最短路,树的直径)https:///problemnew/show/P1099第四节图的连通性问题第五节并查集NOIP2010年提高组第3题P1525关押罪犯(二分答案或并查集)https:///problemnew/show/P1525NOIP2017提高组第4题P3958奶酪(数据结构树结构并查集)https:///problem-12205.htmlhttps:///problemnew/show/P3958第六节最小生成树第七节拓朴排序与关键路径NOIP2013普及组第4题P1983车站分级(图论、拓扑排序) https:///problemnew/show/P19831390:食物链【NOI2001】:8088/problem_show.php?pid=1390NOIP2004年提高组第2题P1090合并果子(最优哈夫曼树,排序,贪心)https:///problemnew/show/P1090NOIP2013年提高组第3题P1967货车运输(最大生成树,最近公共祖先)https:///problemnew/show/P1967NOIP2018提高组第4题P5022旅行(搜索图结构)https:///problem-12397.htmlhttps:///problemnew/show/P5022NOIP2018提高组第6题P5024保卫王国(图结构)https:///problem-12399.htmlhttps:///problemnew/show/P50242、啊哈!算法--2014-06(35-50小时)第二阶段算法与数据结构提高1、《信息学奥赛一本通·提高篇》(80-100课时,不一定一次都讲完)第一部分基础算法第1章贪心算法NOIP2002提高组第1题P1031均分纸牌(贪心,模拟)https:///problemnew/show/P1031NOIP2010普及组第3题P1158导弹拦截(排序+枚举,贪心)https:///problemnew/show/P1158NOIP2012提高组第6题P1084疫情控制(二分答案,贪心,倍增)https:///problemnew/show/P1084第2章二分与三分NOIP2010年提高组第3题P1525关押罪犯(二分答案或并查集)https:///problemnew/show/P1525NOIP2008提高组第4题P1155双栈排序(枚举,贪心/二分图)https:///problemnew/show/P1155NOIP2015提高组第4题P2678跳石头(二分查找、二分答案)https:///problem-12198.htmlhttps:///problemnew/show/P2678第3章深搜的剪枝技巧NOIP2018普及组第4题对称二叉树(搜索树结构深度优先搜索)https:///problem-12396.htmlhttps:///problemnew/show/P5018NOIP2011年提高组第3题P1312Mayan游戏(深搜、剪支)https:///problemnew/show/P1312NOIP2015年提高组第3题P2668斗地主(分情况,剪枝)https:///problemnew/show/P2668NOIP2003提高组第4题P1041传染病控制(随机贪心/搜索剪枝)https:///problemnew/show/P1041NOIP2004提高组第4题P1092虫食算(搜索搜索与剪枝)https:///problem-12414.htmlhttps:///problemnew/show/P1092第4章广搜的优化技巧NOIP2017年普及组第3题棋盘(搜索搜索与剪枝广度优先搜索)https:///problemnew/show/P3956https:///problem-12336.htmlNOIP2009提高组第4题P1074靶形数独(搜索优化)https:///problemnew/show/P1074NOIP2010提高组第4题P1514引入水域(广搜+动态规划,判断有解和无解)https:///problemnew/show/P1514第二部分字符串算法第1章哈希表第2章KMP算法第3章Trie字典树第4章AC自动机NOIP2005提高组第4题P1054等价表达式(字符串,抽样检测,表达式) /practice/1686/https:///problemnew/show/P1054NOIP2008普及组第4题P1058立体图(字符输出)https:///problemnew/show/P1058NOIP2006普及组第3题P1061Jam的计数法(数学、字符串)https:///problemnew/show/P1061NOIP2007年提高组第2题字符串的展开(字符串模拟)https:///problem-11016.htmlhttps:///problemnew/show/P1098NOIP2003年提高组第2题P1039侦探推理(枚举,模拟,字符串)https:///problemnew/show/P1039NOIP2011普及组第2题_P1308统计单词数/ch0112/05/https:///problemnew/show/P1308第三部分图论第1章最小生成树第2章最短路径NOIP2016年提高组第3题P1850换教室(最短路/Dp)https:///problemnew/show/P1850NOIP2017年提高组第3题P3953逛公园(搜索图结构记忆化搜索最短路)https:///problem-12337.htmlhttps:///problemnew/show/P3953NOIP2014提高组第5题P1351联合权值(遍历,二次展开式)https:///problem-12086.htmlhttps:///problemnew/show/P1351第3章SPFA算法的优化第4章差分约束系统第5章强连通分量第6章割点和桥第7章欧拉回路第四部分数据结构第1章树状数组第2章RMQ问题第3章线段树NOIP2012提高组第5题P1083借教室(枚举、线段树、树状数组、二分) https:///problem-12069.htmlhttps:///problemnew/show/P1083NOIP2017提高组第6题P3960列队(数据结构平衡树线段树)https:///problem-12339.htmlhttps:///problemnew/show/P3960第4章倍增求LCANOIP2015提高组第6题P2680运输计划(Lca或线段树)https:///problem-12213.htmlhttps:///problemnew/show/P2680第5章树链剖分第6章平衡树Treap第五部分动态规划第1章区间类型动态规划NOIP2007年提高组第3题P1005矩阵取数游戏(区间DP,高精度)https:///problemnew/show/P1005第2章树型动态规划NOIP2003年提高组第3题P1040加分二叉树(树,区间DP)https:///problemnew/show/P1040第3章数位动态规划第4章状态压缩类动态规划NOIP2017提高组第5题P3959宝藏(动态规划搜索贪心状态压缩DP枚举)https:///problem-12340.htmlhttps:///problemnew/show/P3959NOIP2016提高组第6题愤怒的小鸟(状态压缩动态规划)https:///problemnew/show/P2831第5章单调队列优化动态规划NOIP2016提高组第5题蚯蚓(单调队列)https:///Mrsrz/p/7517155.htmlhttps:///m0_38083668/article/details/82557281NOIP2017普及组第4题P3957跳房子(数据结构动态规划单调队列队列)https:///problem-12338.htmlhttps:///problemnew/show/P3957第6章利用斜率优化动态规划NOIP2012年提高组第3题P1081开车旅行(离线深搜,动态规划、倍增)https:///problemnew/show/P1081NOIP2015提高组第5题P2679子串(Dp+滚动数组)https:///problemnew/show/P2679第六部分数学基础第1章快速幂第2章素数第3章约数第4章同余问题第5章矩阵乘法第6章组合数学NOIP2009年提高组第2题P1072Hankson的趣味题(初等数论,质因数,组合数学)https:///problemnew/show/P1072NOIP2006提高组第4题P10662^k进制数(动态规划/组合数学,高精度) https:///problemnew/show/P1066NOIP2011提高组第4题P1313计算系数(组合、二项式系数)/practice/4036/https:///problemnew/show/P1313NOIP2016提高组第4题P2822组合数问题(杨辉三角)https:///problemnew/show/P2822第7章博弈论NOIP2004普及组第4题P1088火星人(数学:排列、stl)https:///problemnew/show/P1088NOIP2009普及组第3题P1069细胞分裂(数论)https:///problemnew/show/P1069NOIP2000提高组第1题P1017进制转换(初等代数,找规律)https:///problemnew/show/P1017NOIP2001提高组第1题P1024一元三次方程求解(数学,枚举,实数处理) /ch0204/7891/https:///problemnew/show/P1024NOIP2003普及组第3题P1044栈(数学:卡特兰数)https:///problemnew/show/P1044NOIP2018年提高组第2题货币系统(数论)https:///problem-12391.htmlhttps:///problemnew/show/P5020NOIP2014年普及组复赛第3题螺旋矩阵(数学分析)https:///problem-12341.htmlhttps:///problemnew/show/P2239NOIP2015年普及组第3题求和(数学:数列)https:///problemnew/show/P2671NOIP2004普及组第4题P1088火星人(数学:排列、stl)https:///problemnew/show/P1088NOIP2005普及组第4题P1050循环(高精度运算、数论、快速幂) https:///problemnew/show/P1050NOIP2006普及组第4题P1062数列(数学:进制转换)https:///problemnew/show/P1062NOIP2007普及组第4题P1096$Hanoi$双塔问题(数学、高精度) https:///problemnew/show/P1096NOIP2016普及组第4题P2119魔法阵(数学分析、枚举)https:///problemnew/show/P2119NOIP2002年提高组第3题P1033自由落体(数学,物理,模拟,实数处理) https:///problemnew/show/P1033NOIP2005年提高组第3题P1053篝火晚会(置换群,贪心)https:///problemnew/show/P1053NOIP2012提高组第4题P1082同余方程(数论、递归,扩展欧几里得)https:///problemnew/show/P1082NOIP2011提高组第5题P1314聪明的质监员(部分和优化)/practice/4037/https:///problemnew/show/P1314NOIP2013提高组第5题P1970花匠(序列)https:///problem-12072.htmlhttps:///problemnew/show/P1970NOIP2018提高组第5题P5023填数游戏(DP)https:///problem-12398.htmlhttps:///problemnew/show/P50232、NOIP历年真题讲解(30-50小时)---包括初赛和复赛3、《骗分导论》(推荐指数:5颗星)--电子书(可以作为学习的参考资料)第三阶段算法与数据结构高级专题(选择性学习)1、信息学奥赛之数学专题2、高级数据结构(C++版)3、动态规划专题注:上面的内容也可能要交叉的进行讲解在线题库:1、OpenJudge在线题库/2、信息学奥赛一本通在线评测系统:8088/3、洛谷https:///4、啊哈编程/tiku/5、《信息学奥赛一本通(提高篇)》在线评测OJhttps://loj.ac/注:本系列课程将根据行业发展状况,及时优化调整课程内容,具体课程设置以实际为准。
中职C语言基础算法之递推算法
3) 而每头小母牛从第四个年头才开始生育,所以今年可以生育 的母牛的数实际上就是三年前的母牛总数,即为f(n-3)。
第3章 例程序3控:制母结构牛的故事---顺推法
递推公式:
f(n)=f(n-1)+f(n-3) (n>=4)
第3章 程序控制结构
例1:猴子第1天摘下若干个桃子,当即吃了一半 又一个。第2天又把剩下的桃吃了一半又一个,以 后每天都吃前一天剩下的桃子的一半又一个,到第 10天猴子想吃时,只剩下一个桃子。
问:猴子第1天一共摘了多少桃子?ห้องสมุดไป่ตู้
分析:
已知条件:第 10 天剩下 1 个桃子; 隐含条件:每一次前一天的桃子个数等于后一天 桃子的个数加 1 的 2 倍。 逆向思维:从后往前推,可用倒推法求解。
④ int i,n;
⑤ scanf("%d",&n);
⑥ f[1]=1; f[2]=2; f[3]=3;
⑦ for(i=4; i<=n; i++)
⑧
{ f[i]=f[i-3]+f[i-1];
⑨ ⑩}
printf("%Id\n",f[i]);
2
s2=s3*5/4+1
s5必须是整数
1
s1=s2*5/4+1
通过递推,求出s1即可
第3章 程序控制结构
//例2:猴子分食桃子---逆推法
#include <stdio.h> void main() { int x,s,k,i;
x=6; // 最少的初值 k=0; // 整除标志 while ( k!=4) { s=x; k=0;
计算机算法:递推法
递推法递推是计算机数值算法中的重要算法。
递推的思路是通过数学推导将复杂的运算化解为若干重复的简单运算,以充分发挥计算机擅长重复处理的特点。
递推法通过已知条件,利用特定关系得出中间推论,直至得到结果的算法。
递推法的解题步骤:⑴按次序研究集合中最初最原始的若干问题。
⑵按次序寻求集合中问题间的转换规律即递推关系,使问题逐次转化成较低层级或简单的且能解决问题的或已解决的问题。
递推法在解题中的应用:递推法在解题中的应用十分广泛,递推法的特征是化难为易、化繁为简。
使用递推法时,先考虑与题目有关系的另一个较为简单的问题,并加以解决。
然后以此为基础,寻求规律,一步一步递推出原题的解答。
按照推导问题的方向递推分为逆推法和顺推法两种。
所谓顺推法是从已知条件出发,逐步推算出要解决的问题的方法叫顺推。
所谓逆推法从已知问题的结果出发,用迭代表达式逐步推算出问题的开始的条件,即顺推法的逆过程,称为逆推。
示例1:逆推法示例。
猴子第1天摘下若干个桃子,当即吃了一半又一个。
第2天又把剩下的桃吃了一半有一个,以后每天都吃前一天剩下的桃子的一半又一个,到第10天猴子想吃的时候,只剩下一个桃子。
问猴子第1天一共摘了多少桃子?【分析】已知条件第10天剩下1个桃子,隐含条件每一次前一天的桃子个数等于后一天桃子的个数加1的2倍。
采用逆向思维的方法,从后往前推,可用逆推法求解。
【算法】算法描述如下:#include<stdio.h>Main(){ int a=1,I;For (i=9;i>=1;i--)a=(a+1)*2Printf(“%d”,a);}示例2:顺推法示例。
有一段楼梯有10段台阶,规定每一步只能跨一级或两级,问:要登上第10级台阶有多少种不同的走法?【分析】跨到第二级台阶,可以每次跨一级,也可以一次跨二级,共有2种不同的走法。
第三级台阶,可以由第一级台阶跨二级台阶到达,也可以由第二级台阶跨一级到达。
而到达第一级和第二级台阶各有1、2种不同的走法,所以到达第三级台阶共有1+2=3种不同的走法。
算法与数据结构C语言版课后习题答案(机械工业出版社)第3,4章习题参考答案
算法与数据结构C语⾔版课后习题答案(机械⼯业出版社)第3,4章习题参考答案第3章栈和队列⼀、基础知识题3.1有五个数依次进栈:1,2,3,4,5。
在各种出栈的序列中,以3,4先出的序列有哪⼏个。
(3在4之前出栈)。
【解答】34215 ,34251,345213.2铁路进⾏列车调度时,常把站台设计成栈式结构,若进站的六辆列车顺序为:1,2,3,4,5,6,那么是否能够得到435612, 325641, 154623和135426的出站序列,如果不能,说明为什么不能;如果能,说明如何得到(即写出"进栈"或"出栈"的序列)。
【解答】输⼊序列为123456,不能得出435612和154623。
不能得到435612的理由是,输出序列最后两元素是12,前⾯4个元素(4356)得到后,栈中元素剩12,且2在栈顶,不可能让栈底元素1在栈顶元素2之前出栈。
不能得到154623的理由类似,当栈中元素只剩23,且3在栈顶,2不可能先于3出栈。
得到325641的过程如下:1 2 3顺序⼊栈,32出栈,得到部分输出序列32;然后45⼊栈,5出栈,部分输出序列变为325;接着6⼊栈并退栈,部分输出序列变为3256;最后41退栈,得最终结果325641。
得到135426的过程如下:1⼊栈并出栈,得到部分输出序列1;然后2和3⼊栈,3出栈,部分输出序列变为13;接着4和5⼊栈,5,4和2依次出栈,部分输出序列变为13542;最后6⼊栈并退栈,得最终结果135426。
3.3若⽤⼀个⼤⼩为6的数组来实现循环队列,且当前rear和front的值分别为0和3,当从队列中删除⼀个元素,再加⼊两个元素后,rear和front的值分别为多少?【解答】2和43.4设栈S和队列Q的初始状态为空,元素e1,e2,e3,e4,e5和e6依次通过栈S,⼀个元素出栈后即进队列Q,若6个元素出队的序列是e3,e5,e4,e6,e2,e1,则栈S的容量⾄少应该是多少?【解答】43.5循环队列的优点是什么,如何判断“空”和“满”。
C语言递归算法PPT演示课件
for (k=1;k<=10;k++)
cin>>a[k];
cin>>x;
search(x,L,R);
system("pause");
} void search(int x,int top,int bot) //二分查找递归过程
{
int mid;
if (top<=bot)
{ mid=(top+bot)/2;
an加入到k个子集中的任一个中去,共有k种加入方式,这样对
于an的每一种加入方式,都可以使集合划分为k个子集,因此
根据乘法原理,划分数共有k * S(n-1,k)个。
•16
综合上述两种情况,应用加法原理,得出n个元素的集合 {a1,a2,……,an}划分为k个子集的划分数为以下递归公 式:S(n,k)=S(n-1,k-1) + k * S(n-1,k) (n>k,k>0)。
确定n个元素a1 ,a2 ,……,an 放入k个无标号盒子中去
的划分数S(n,k)。
【输入样例】setsub.in
23 7
【输出样例】setsub.out
4382641999117305
•15
【算法分析】
先举个例子,设S={1,2,3,4},k=3,不难得出S有 6种不同的划分方案,即划分数S(4,3)=6,具体方案为:
int s(int n, int k)
//数据还有可能越界,请用高精度计算
{
if ((n < k) || (k == 0)) return 0;
//满足边界条件,退出
if ((k == 1) || (k == n)) return 1;
C语言递推与递归PPT课件
• void qsort(int array[], int start, int end) • 把数组下标为start到end的元素进行快速排序第18页/共25页快速排序问题5
7
3
8
1
4
2
6
2
7
3
8
1
4
5
6
2
5
3
8
1
4
7
6
2
4
3
8
1
5
7
6
2
4
3
5
1
8
7
6
2
4
3
1
5
8
7
6
1
4
3
2
第16页/共25页
汉诺塔问题
第17页/共25页
快速排序问题
• 快速排序思路如下
• 将要排序的数据放在数组array中 • 取a[0]变在变量m中,通过分区处理把m排在适当的位置,使
m左边的数都比m小,m右边的数都比m大 • 按照常上面的思路分别处理m左边和右边的数据 • 如果分区长度是1,停止处理
• 思路提示
• m个球取出来的n个,包含两种情况:n在其中和n不在其中
• 编程实现
• 使用递归思想 • 编写递归函数 int cmn(int m, int n)
第12页/共25页
计算组合数
第13页/共25页
汉诺塔问题
• 据说在古代印度bramah神庙中,有个和尚整天把3根 柱子上的金盘倒来倒去。初始在柱子A上有64个盘子串 在一起,每一个盘子都比它下面的盘子小,可以在ABC 三个柱子之间互相移动,最终要全部移动到柱子C上。 移动规则如下:每次只允许移动一个,且较大的盘子永 远不能放在较小的盘子上。
c语言递推法
c语言递推法递推法是通过已知的一些值,推算出其他未知值的方法。
在C语言中,递推法可以用循环语句实现。
常见的递推法有斐波那契数列、杨辉三角等。
下面以斐波那契数列为例,介绍一下C语言中递推法的实现。
斐波那契数列是指: 0, 1, 1, 2, 3, 5, 8, 13, 21, ....数列中第0项为0,第1项为1,从第2项开始,每一项都是前两项的和。
通过递推法可以利用前两项的值计算出后面的值。
具体实现可以使用循环语句,代码如下:```c#include <stdio.h>int main() {int n, i, f1 = 0, f2 = 1, f3; // 定义n为要计算的项数, f1, f2为前两项的值,f3为要计算的当前项数的值printf("请输入要计算的项数:");scanf("%d", &n);printf("斐波那契数列的前%d项为:\n", n);printf("%d %d ", f1, f2); // 输出前两项的值for (i = 0; i < n-2; i++) { // 从第三项开始循环f3 = f1 + f2; // 计算当前项的值printf("%d ", f3); // 输出当前项的值f1 = f2; // 更新前两项的值f2 = f3;}printf("\n");return 0;```在上述代码中,通过定义变量f1、f2和f3,分别表示斐波那契数列的前两项和当前要计算的项。
在循环中,先计算出当前项的值,并输出。
然后更新前两项的值,继续循环下一项的计算,直到计算完成。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
【算法分析】 方法一:排列组合(但需要运用动态规划)。 可以列出公式,在n个格子中放x个3(其中x为偶数,包括0).。 c(n,x)*9^(n-x)-c(n-1,x)*9^(n-x-1) 含义为在n个格子中取x个3,且不考 虑第一位的特殊情况为c(n,x)*9^(n-x)。 而第一位为0的情况,为c(n-1,x)*9^(n-x-1),两者减下,就为答案。 方法二:递推 考虑这种题目,一般来说都是从第i-1位推导第i位,且当前位是取偶数 还是取奇数的。 恍然大悟.可以用f[i][0]表示前i位取偶数个3有几种情况,f[i][1]表示前i位 取奇数个3有几种情况。 则状态转移方程可以表示为: f[i][0]=f[i-1][0]*9+f[i-1][1];f[i][1]=f[i-1][0]+f[i-1][1]*9; 边界条件:f[1][1]=1;f[1][0]=9;
【例4】昆虫繁殖 【问题描述】 科学家在热带森林中发现了一种特殊的昆虫,这种昆虫的繁殖能力很强。 每对成虫过x个月产y对卵,每对卵要过两个月长成成虫。假设每个成虫 不死,第一个月只有一对成虫,且卵长成成虫后的第一个月不产卵(过X 个月产卵),问过Z个月以后,共有成虫多少对? 0=<X<=20,1<=Y<=20,X=<Z<=50 【输入格式】 x,y,z的数值 【输出格式】 过Z个月以后,共有成虫对数 【输入样例】 128 【输出样例】 37
(4)当n=3时:骨牌可以全部竖排,也可以认为在方格中已经有一个竖排 骨牌,则需要在方格中排列两个横排骨牌(无重复方法),若已经在方格中排 列两个横排骨牌,则必须在方格中排列一个竖排骨牌。如上右图,再无其他排 列方法,因此铺法总数表示为x3=3。 由此可以看出,当n=3时的排列骨牌的方法数是n=1和n=2排列方法数的 和。 (5)推出一般规律:对一般的n,要求xn可以这样来考虑,若第一个骨牌是 竖排列放置,剩下有n-1个骨牌需要排列,这时排列方法数为xn-1;若第一个骨 牌是横排列,整个方格至少有2个骨牌是横排列(1*2骨牌),因此剩下n-2个 骨牌需要排列,这是骨牌排列方法数为xn-2。从第一骨牌排列方法考虑,只有 这两种可能,所以有: xn=xn-1+xn-2 (n>2) x1=1 x2=2 xn=xn-1+xn-2就是问题求解的递推公式。任给n都可以从中获得解答。例如n=5, x3=x2+x1=3 x4=x3+x2=5 x5=x4+x3=8
下面是输入n,输出x1~xn的c++程序: #include<iostream> using namespace std; int main() { int n,i,j,a[101]; cout<<"input n:"; //输入骨牌数 cin>>n; a[1]=1;a[2]=2; cout<<"x[1]="<<a[1]<<endl; cout<<"x[2]="<<a[2]<<endl; for (i=3;i<=n;i++) //递推过程 { a[i]=a[i-1]+a[i-2]; cout<<"x["<<i<<"]="<<a[i]<<endl; } } 下面是运行程序输入 n=30,输出的结果: input n: 30 x[1]=1 x[2]=2 x[3]=3 ........ x[29]=832040 x[30]=1346269
【算法分析】 跳马是一道老得不能再老的题目,我想每位编程初学者都学过,可能是 在学回溯或搜索等算法的时候,很多书上也有类似的题目,一些比赛中也 出现过这一问题的变形(如NOIP1997初中组的第三题)。有些同学一看 到这条题目就去搜索,即使你编程调试全通过了,运行时你也会发现:当 n,m=15就会超时。 其实,本题稍加分析就能发现,要到达棋盘上的一个点,只能从左边过 来(我们称之为左点)或是从上面过来(我们称之为上点),所以根据加 法原理,到达某一点的路径数目,就等于到达其相邻的上点和左点的路径 数目之和,因此我们可以使用逐列(或逐行)递推的方法来求出从起点到 终点的路径数目。障碍点(马的控制点)也完全适用,只要将到达该点的 路径数目设置为0即可。 用F[i][j]表示到达点(i,j)的路径数目,g[i][j]表示点(i, j)有无障碍,g[i][j]=0 表示无障碍,g[i][j]=1表示有障碍。 则,递推关系式如下: F[i][j] = F[i-1][j] + F[i][j-1] //i>0且j>0且g[i][j]= 0 递推边界有4个: F[i][j] = 0 //g[i][j] = 1 F[i][0] = F[i-1][0] //i > 0且g[i][0] = 0 F[0][j] = F[0][j-1] //j > 0且g[0][j] = 0 F[0][0] = 1 考虑到最大情况下:n=20,m=20,路径条数可能会超过231-1,所以要用 高精度。
还是先找找规律。 第1个月:一对新兔子r1。用小写字母表示新兔子。 第2个月:还是一对新兔子,不过已经长大,具备生育能力了, 用大写字母R1表示。 第3个月:R1生了一对新兔子r2,一共2对。 第4个月:R1又生一对新兔子r3,一共3对。另外,r2长大了,变 成R2 第5个月:R1和R2各生一对,记为r4和r5,共5对。此外,r3长 成R3。 第6个月:R1、R2和R3各生一对,记为r6~r8,共8对。此外, r4和r5长大。 …… 把这些数排列起来:1,1,2,3,5,8,……,事实上,可以 直接推导出来递推关系f(n)=f(n-1)+f(n-2):第n个月的兔子由两部分组成 ,一部分是上个月就有的老兔子f(n-1),一部分是这个月出生的新兔子 f(n-2)(第n个月时具有生育能力的兔子数就等于第n-2个月兔子总数)。 根据加法原理,f(n)=f(n-1)+f(n-2)。
第三章 递推算法
递推法是一种重要的数学方法,在数学的各个领域中都 有广泛的运用,也是计算机用于数值计算的一个重要算法。 这种算法特点是:一个问题的求解需一系列的计算,在已知 条件和所求问题之间总存在着某种相互联系的关系,在计算 时,如果可以找到前后过程之间的数量关系(即递推式), 那么,从问题出发逐步推到已知条件,此种方法叫逆推。无 论顺推还是逆推,其关键是要找到递推式。这种处理问题的 方法能使复杂运算化为若干步重复的简单运算,充分发挥出 计算机擅长于重复处理的特点。 递推算法的首要问题是得到相邻的数据项间的关系(即 递推关系)。递推算法避开了求通项公式的麻烦,把一个复 杂的问题的求解,分解成了连续的若干步简单运算。一般说 来,可以将递推算法看成是一种特殊的迭代算法。
【例1】数字三角形。如下所示为一个数字三角形。请编一个程序计算从顶到 底的某处的一条路径,使该路径所经过的数字总和最大。只要求输出总和。 1、 一步可沿左斜线向下或右斜线向下走; 2、 三角形行数小于等于100; 3、 三角形中的数字为0,1,…,99; 测试数据通过键盘逐行输入,如上例数据应以如下所示格式输入: 5 7 38 810 2744 45265 【算法分析】 此题解法有多种,从递推的思想出发,设想,当从顶层沿某条路径走到第i 层向第i+1层前进时,我们的选择一定是沿其下两条可行路径中最大数字的方向 前进,为此,我们可以采用倒推的手法,设a[i][j]存放从i,j 出发到达n层的最大 值,则a[i][j]=max{a[i][j]+a[i+1][j],a[i][j]+a[i+1][j+1]},a[1][1] 即为所求的数字总 和的最大值。
【例5】位数问题 【问题描述】 在所有的N位数中,有多少个数中有偶数个数字3?由于结果可能很 大,你只需要输出这个答案对12345取余的值。 【输入格式】 读入一个数N 【输出格式】 输出有多少个数中有偶数个数字3。 【输入样例】 2 【输出样例】 73 【数据规模】 1<=N<=1000 【样例说明】 在所有的2位数字,包含0个3的数有72个,包含2个3的数有1个,共73 个
程序如下: #include<iostream> #include<cstdio> using namespace std; int main() { int f0=1,f1=1,f2; int n;ቤተ መጻሕፍቲ ባይዱcin>>n;
for (int i=3; i<=n; ++i) { f2=f0+f1; f0=f1; f1=f2; } printf("%d\n",f2); return 0; }
【例6】过河卒(Noip2002) 【问题描述】 棋盘上A点有一个过河卒,需要走到目标B点。卒行走的规则:可以向 下、或者向右。同时在棋盘上的任一点有一个对方的马(如C点),该马 所在的点和所有跳跃一步可达的点称为对方马的控制点,如图3-1中的C点 和P1,……,P8,卒不能通过对方马的控制点。棋盘用坐标表示,A点 (0,0)、B点(n, m) (n,m为不超过20的整数),同样马的位置坐标是需要给 出的,C≠A且C≠B。现在要求你计算出卒从A点能够到达B点的路径的条数。
【参考程序】 #include<iostream> using namespace std; int main() { long long a[101]={0},b[101]={0},i,j,x,y,z; cin>>x>>y>>z; for(i=1;i<=x;i++){a[i]=1;b[i]=0;} for(i=x+1;i<=z+1;i++) //因为要统计到第z个月后,所以要for到z+1 { b[i]=y*a[i-x]; a[i]=a[i-1]+b[i-2]; } cout<<a[z+1]<<endl; return 0; }