众所周知,斐波那契数列是非常经典的一个数列,它的数学公式如下

为了便于观察,我们列出它的几项:0  1  1  2  3  5  8  13  21......

下面我们将介绍四种方法来用C语言计算机代码实现对斐波那契数列的求解,分别是:递归法,迭代法,矩阵求解法以及特殊性质公式。

一、递归法

(PS:没有递归基础的建议先学习递归的基础概念,在此我仅简要介绍一下递归的思想和求解代码)

在递归的实现中,我们知道,递归有两个要求:(1)进行递归这一操作所需要满足的条件 (2)此条件需要最终不被满足,使得函数的嵌套调用能够返回。在斐波那契数列中,我们知道当x=0时,返回值为0;当x=1时,返回值为1。所以,要求(1)中所需要满足的条件即x>=2;而要求(2)中要使该条件最终不被满足,即x不断减小,且最终为0或1。

于是我们给出代码的实现:

int Fibonacci(int x)
{if (x >= 2)return Fibonacci(x - 1) + Fibonacci(x - 2);    //当x>=2时,继续按照公式f(x)=f(x-1)+f(x-2)嵌套调用else if (x == 1)return 1;    //当x=1时,返回1,同时嵌套调用开始返回elsereturn 0;    //当x=0时,返回0,同时嵌套调用开始返回
}

用递归的方法求解斐波那契数列是不是非常简单呢?

然而! 用递归的方法也有一个很大的缺点:栈溢出!

栈:函数及其形参的空间由栈分配,在函数调用未完成时,为其分配的空间并不会销毁!于是当递归中函数的调用次数过多时,会导致栈溢出的问题。在本题的递归中,我们能发现,当我们求

F(5)= F(4)+F(3)

= F(3)+F(2)+F(2)+F(1)

= F(2)+F(1)+F(1)+F(0)+F(1)+F(0)+F(1)时,不仅对F(2)进行了多次调用,甚至还进行了多次计算!这就导致计算效率的大幅降低以及资源占用的大幅增加。

于是我们给出第二种方法。

二、迭代法

什么是迭代法?

迭代法也称辗转法,是一种不断用变量的旧值递推新值的过程。

也就是说,这是一种各个变量直接相互作用的过程。

分析思路:设有a、b、c三个变量,以及我们输入的第x项的x,令a=0(第一个斐波那契数)b=1(第二个斐波那契数),当x>=2时,c=a+b,同时再令a、b分别往右移一个数,如此往复x-2次,c的值就变成了第x个数的值。

下面给出代码:

int Fibonacci(int x)
{int a = 0;int b = 1;int c = 0;if (x == 1)return 1;    //当x=1,返回1if (x == 0)return 0;    //当x=0,返回0while (x >= 2)   //输入x>=2时,进行迭代{c = a + b;   //每次迭代令c=a+b,即进行f(x)=f(x-1)+f(x-2)a = b;       //使得a,b往后移一个数字b = c;x--;}return c;
}

三、特殊性质公式法

同递归法,只不过需要用到公式:

                F(n+m)=F(m)*F(n+1)+F(m-1)*F(n)

在这个公式下,F(x)可以转换为F((x/2)   +   x-(x/2)),即一种二分思想,可以将时间复杂度为O(n)的算法转化为时间复杂度为O(log n)的算法。

下面给出代码:

int Fibonacci(int x)
{if (x == 1 || x == 2)    //当x=2时也要返回1,否则将进入死循环。return 1;if (x == 0)return 0;int a = x / 2;int b = x - a;return Fibonacci(a + 1) * Fibonacci(b) + Fibonacci(a) * Fibonacci(b - 1);
}

然而虽然但是事实上这个方法还是不如迭代法来得实在的QoQ

四、矩阵法

于是,只要先算出系数矩阵的n-1次幂,再用与之相乘即可求出F(n)

下面是用矩阵快速幂的方法求出所需矩阵n-1次幂的代码:

(PS:小编只学了快速幂,这个矩阵快速幂的算法是自己琢磨出来的,可能不标准,如果有心可以去学一下矩阵快速幂的算法!!下面会给出一般快速幂的算法给各位小可爱们参考一下~)

int Fibonacci(int x)
{if (x == 0)return 0;if (x == 1 || x == 2)return 1;int a[2][2] = { {1,1},{1,0} };int b[2][2] = { {1,1},{1,0} };int c[2][2] = { {1,0},{0,1} };int d[2][2] = { {1,0},{0,1} };int t = x - 1;while (t){if (t%2==1){d[0][0] = c[0][0] * b[0][0] + c[0][1] * b[1][0];d[0][1] = c[0][0] * b[0][1] + c[0][1] * b[1][1];d[1][0] = c[1][0] * b[0][0] + c[1][1] * b[1][0];d[1][1] = c[1][0] * b[0][1] + c[1][1] * b[1][1];c[0][0] = d[0][0];c[0][1] = d[0][1];c[1][0] = d[1][0];c[1][1] = d[1][1];}b[0][0] = a[0][0] * a[0][0] + a[0][1] * a[1][0];b[0][1] = a[0][0] * a[0][1] + a[0][1] * a[1][1];b[1][0] = a[1][0] * a[0][0] + a[1][1] * a[1][0];b[1][1] = a[1][0] * a[0][1] + a[1][1] * a[1][1];  a[0][0] = b[0][0];a[0][1] = b[0][1];a[1][0] = b[1][0];a[1][1] = b[1][1];t >>= 1;}return c[0][0];
}

其中F(x) = c[0][0]*F(1)+c[1][0]*F(0) = c[0][0]

快速幂代码:

int f(int a,int n)
{int ans = 1;while (n){if (n & 1 == 1)    //判断n的最后一位是否为1{ans *= a;}a *= a;            //a每次自乘a,使得a在每次循环中分别为a,a^2,a^3...n >>= 1;           //n右移一,使得n的二进制表示中1所在的位置所代表的位全与a当前的次幂相同}return ans;
}

好啦这就是全部内容啦!!!

C语言实现求解斐波那契数列的四种方法及优化处理(递归,迭代,特殊性质公式,矩阵快速幂)相关推荐

  1. Python中斐波那契数列的四种写法

    在这些时候,我可以附和着笑,项目经理是决不责备的.而且项目经理见了孔乙己,也每每这样问他,引人发笑.孔乙己自己知道不能和他们谈天,便只好向新人说话.有一回对我说道,"你学过数据结构吗?&qu ...

  2. 剑指offer——面试题9:求斐波那切数列的四种方法

    剑指offer--面试题9:求斐波那切数列的四种方法 另一个相关的链接:https://blog.csdn.net/Allenlzcoder/article/details/80297333 总结下求 ...

  3. C语言--斐波那契数列(三种方法)

    文章目录 一·介绍 二·代码实现 1·递归实现 2·迭代实现 3·数组实现 一·介绍 斐波那契数列,就是前两个数是1,之后从第三个数开始等于前面两个数的和,请用代码方式求出第n个斐波那契数列的大小. ...

  4. C语言斐波那契数列求和两种方法

    递归调用函数: #define _CRT_SECURE_NO_WARNINGS int fun(int n); #include<stdio.h> int main() {//斐波那契数列 ...

  5. 斐波那契数列的四种实现方式(C语言)

    斐波那契数列是一组第一位和第二位为1,从第三位开始,后一位是前两位和的一组递增数列, 像这样的:1.1.2.3.5.8.13.21.34.55...... 今天,我们用四种方式来进行实现: 1.递归 ...

  6. C语言实现斐波那契数列的几种方法

    斐波那契数列指的是这样一个数列:1 .1.2.3.5.8.13.21.34.55.89--是从第三项开始每一项都是前两项之和. 用递推的方法定义为: f(0)=1;f(1)=1; f(n)=f(n-1 ...

  7. 剑指Offer #07 斐波那契数列(四种解法)| 图文详解

    题目来源:牛客网-剑指Offer专题 题目地址:斐波那契数列 题目描述 大家都知道斐波那契数列,现在要求输入一个整数n,请你输出斐波那契数列的第n项(从0开始,第0项为0).n<=39 题目解析 ...

  8. 斐波那契数列的四种实现

    来自:Crossin的编程教室 孔乙己自己知道不能和他们谈天,便只好向 Intern 说话.有一回对我说道,"你写过代码么?"我略略点一点头.他说,"写过代码,--我便考 ...

  9. C++输出斐波那契数列的几种方法

    定义: 斐波那契数列指的是这样一个数列:0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, ... 这个数列从第三项开始,每一项都等于前两项之和. 以输出斐波那 ...

最新文章

  1. 【转】C++的面象对象总结
  2. opencv4 c++ 提取图片中的白色区域_修正!【从零学习OpenCV 4】分割图像——分水岭法...
  3. 《算法竞赛进阶指南》打卡-基本算法-AcWing 97. 约数之和:递归、快速幂
  4. zabbix如何选择适合的监控类型(107)
  5. jmeter进行https协议的测试
  6. android-线程池-最顺手的写法
  7. LeetCode 1566. 重复至少 K 次且长度为 M 的模式
  8. 职称计算机承诺书,职称申报承诺书范本
  9. php而且,PHP – David's Blog
  10. 分享一个Ubuntu16.0.4安装MySQL5.7脚本
  11. 工具的使用——搜狗输入法
  12. Android5更新包,Android5.1无法完成整包的更新
  13. 如何构建NTP时间服务器
  14. podman加速器harbor私有镜像仓库
  15. testbed代码审查信息提取
  16. [gitHub使用笔记一]ubuntu下快速访问github官网的方法
  17. 小伙伴们要的飞机大战代码 简易入门版
  18. 桂电计算机系入学怎么分班,桂电研究生-()学期课程总表
  19. 计算机上安装了更新ie版本,电脑XP系统安装不了ie提示“安装了更新的Internet Explorer版本”的解决方法...
  20. Windows Update错误80070003解决方法

热门文章

  1. 金融科技之:互联网贷款系统平台建设方案分享
  2. 【操作系统】30天自制操作系统--(14)多任务1
  3. JSP: Taglib
  4. 一篇全了解Spring全注解详解
  5. 酷视网页视频VR播放器SDK(旗舰版)使用说明书
  6. iOS随机生成验证码
  7. 2019,淘宝无货源转型之路势在必行,单类目玩法实操案例解析
  8. Android偏好设置的使用
  9. 解决win7“点击图片出现预览窗格”的问题
  10. 计算机开机后嘟嘟响,笔记本电脑发出嘟嘟嘟的声音