如何使用Python实现斐波那契数列


Posted in Python onJuly 02, 2019

斐波那契数列(Fibonacci)最早由印度数学家Gopala提出,而第一个真正研究斐波那契数列的是意大利数学家 Leonardo Fibonacci,斐波那契数列的定义很简单,用数学函数可表示为:

如何使用Python实现斐波那契数列

数列从0和1开始,之后的数由前两个数相加而得出,例如斐波那契数列的前10个数是:0, 1, 1, 2, 3, 5, 8, 13, 21, 34。

用 Python 实现斐波那契数列常见的写法有三种,各算法的执行效率也有很大差别,在面试中也会偶尔会被问到,通常面试的时候不是让你简单的用递归写写就完了,还会问你时间复杂度怎样,空间复杂度怎样,有没有可改进的地方。

递归法

所谓递归就是指函数的定义中使用了函数自身的方法

def fib_recur(n):
assert n >= 0
if n in (0, 1):
return n
return fib_recur(n - 1) + fib_recur(n - 2)
for i in range(20):
print(fib_recur(i), end=" ")
>>> 0 1 1 2 3 5 8 13 21 34 55 89 144 233 377 610 987 1597 2584 4181

递归是一种代码最简洁的方法,但它是效率非常低,因为会出现大量的重复计算,时间复杂度是:O(1.618 ^ n),1.618是黄金分割。同时受限于 Python 中递归的最大深度是 1000,所以用递归来求解并不是一种可取的办法。

递推法

递推法就是从0和1开始,前两项相加逐个求出第3、第4个数,直到求出第n个数的值

def fib_loop(n):
a, b = 0, 1
for i in range(n):
a, b = b, a + b
return a
for i in range(20):
print(fib_loop(i), end=" ")
>>> 0 1 1 2 3 5 8 13 21 34 55 89 144 233 377 610 987 1597 2584 4181

这种算法的时间复杂是O(n),呈线性增长,如果数据量巨大,速度越到后面会越慢。

上面两种方式都是使用分而治之的思想,就是把一个大的问题化小,然后利用小问题的求解得到目标问题的答案。

矩阵法

《线性代数》是大学计算机专业低年级的课程,这门课教的就是矩阵,那时候觉得这东西学起来很枯燥,没什么用处,工作后你才发现搞机器学习、数据分析、数据建模时大有用处,书到用时方恨少。其实矩阵的本质就是线性方程式。

斐波那契数列中两个相邻的项分别为:F(n) 和 F(n - 1),如果把这两个数当作一个2行1列的矩阵可表示为:

如何使用Python实现斐波那契数列

因为 F(n) = F(n-1)+F(n-2),所以就有:

如何使用Python实现斐波那契数列

通过反推,其实它是两个矩阵的乘积得来的

如何使用Python实现斐波那契数列

依此类推:

如何使用Python实现斐波那契数列

最后可推出:

如何使用Python实现斐波那契数列

因此想要求出F(n)的值,只要能求出右边矩阵的n-1次方的值,最后求得两矩阵乘积,取新矩阵的第一行的第一列的值即可,比如n=3时,

如何使用Python实现斐波那契数列

​可以得知F(3)的值2,F(2)的值为1,因为幂运算可以使用二分加速,所以矩阵法的时间复杂度为 O(log n)

我们可以用科学计算包 numpy 来实现矩阵法:

import numpy
def fib_matr(n):
return (numpy.matrix([[1, 1], [1, 0]]) ** (n - 1) * numpy.matrix([[1], [0]]))[0, 0]
for i in range(20):
print(int(fib_matr(i)), end=" ")
>>> 0 1 1 2 3 5 8 13 21 34 55 89 144 233 377 610 987 1597 2584 4181

3中不同的算法效率对比:

如何使用Python实现斐波那契数列

从上面图可以看出递归法效率惊人的低,矩阵法在数据量比较大的时候才突显出它的优势,递推法随着数据的变大,所花的时间也越来越大。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
Python画图学习入门教程
Jul 01 Python
python使用response.read()接收json数据的实例
Dec 19 Python
python如何实现代码检查
Jun 28 Python
用Python识别人脸,人种等各种信息
Jul 15 Python
Django admin.py 在修改/添加表单界面显示额外字段的方法
Aug 22 Python
Django 删除upload_to文件的步骤
Mar 30 Python
解决windows上安装tensorflow时报错,“DLL load failed: 找不到指定的模块”的问题
May 20 Python
Python代码需要缩进吗
Jul 01 Python
Python实现Canny及Hough算法代码实例解析
Aug 06 Python
使用Python将语音转换为文本的方法
Aug 10 Python
Python3 用matplotlib绘制sigmoid函数的案例
Dec 11 Python
Python+Matplotlib图像上指定坐标的位置添加文本标签与注释
Apr 11 Python
pandas数据筛选和csv操作的实现方法
Jul 02 #Python
Python列表与元组的异同详解
Jul 02 #Python
Pandas中resample方法详解
Jul 02 #Python
Python何时应该使用Lambda函数
Jul 02 #Python
Python Pandas分组聚合的实现方法
Jul 02 #Python
使用Python做垃圾分类的原理及实例代码附源码
Jul 02 #Python
python flask框架实现重定向功能示例
Jul 02 #Python
You might like
海贼王:最美的悬赏令!
2020/03/02 日漫
php中使用DOM类读取XML文件的实现代码
2011/12/14 PHP
浅谈PHP中的数据传输CURL
2016/09/06 PHP
php让json_encode不自动转义斜杠“/”的方法
2020/04/27 PHP
一个js实现的所谓的滑动门
2007/05/23 Javascript
JS代码放在head和body中的区别分析
2011/12/01 Javascript
json的前台操作和后台操作实现代码
2012/01/20 Javascript
js模拟滚动条(横向竖向)
2013/02/22 Javascript
JavaScript中setAttribute用法介绍
2013/07/20 Javascript
处理及遍历XML文档DOM元素属性及方法整理
2013/08/23 Javascript
jQuery的几个我们必须了解的特点
2015/05/03 Javascript
jQuery取消ajax请求的方法
2015/06/09 Javascript
再JavaScript的jQuery库中编写动画效果的指南
2015/08/13 Javascript
js实现页面跳转的五种方法推荐
2016/03/10 Javascript
微信小程序 图片等比例缩放(图片自适应屏幕)
2016/11/16 Javascript
jQuery事件绑定方法学习总结(推荐)
2016/11/21 Javascript
使用Angular缓存父页面数据的方法
2017/01/03 Javascript
js实现百度搜索提示框
2017/02/05 Javascript
js绑定事件和解绑事件
2017/04/27 Javascript
对Vue- 动态元素属性及v-bind和v-model的区别详解
2018/08/27 Javascript
解决vue 项目引入字体图标报错、不显示等问题
2018/09/01 Javascript
python实现二分查找算法
2017/09/21 Python
python kmeans聚类简单介绍和实现代码
2018/02/23 Python
对python多线程中Lock()与RLock()锁详解
2019/01/11 Python
Python爬虫之Selenium实现键盘事件
2020/12/04 Python
html5与css3小应用
2013/04/03 HTML / CSS
美国宠物用品网站:Value Pet Supplies
2018/03/17 全球购物
应届毕业生求职信范文
2014/05/08 职场文书
公司合作意向书范文
2014/07/30 职场文书
药店促销活动策划方案
2014/08/24 职场文书
标准版离职证明书
2014/09/12 职场文书
绿色环保倡议书
2015/04/28 职场文书
求职自我评价参考范文
2019/05/16 职场文书
python中__slots__节约内存的具体做法
2021/07/04 Python
基于Python实现一个春节倒计时脚本
2022/01/22 Python
《巫师》是美食游戏?CDPR10月将推出《巫师》官方食谱
2022/04/03 其他游戏