• 斐波那契数列-python实现


    斐波那契数列(黄金分割数列)指的是这样一个数列 0, 1, 1, 2, 3, 5, 8, 13,特别指出:第0项是0,第1项是第一个1。从第三项开始,每一项都等于前两项之和。
     
    Python 实现斐波那契数列代码如下:
    实现一:
     1 def fibonacci():
     2     num = input("Please input your number
    ")
     3     i,a,b= 0,0,1           //赋值
     4     if int(num) < 0:
     5         print("你输入的数据不合理")
     6     elif int(num)== 1:
     7         print(a)
     8     else:
     9         while i < int(num):
    10             print(a)
    11             #sum  = a+b
    12             #a = b
    13             #b = sum
    14             a, b = b, a + b  #a, b = b, a + b这里不能写成 a=b   b=a+b,如果写成这样,b就不是前两位相加的值,而是已经被b赋过值的a和b相加的值
    15             i+=1
    16 fibonacci()
    实现二:
        使用列表的方式实现
    1 def fibonacci(num):
    2     fibs = [0,1]
    3     for i in range(num-2):
    4         fibs.append(fibs[-2]+fibs[-1])   #倒数第二个+倒数第一个数的结果,追加到列表
    5     print(fibs)
    6     
    7 fibonacci(5)
    实现三:
        以上两种方式,都是直接调用的函数中的print打印,return值为none,因此无法进行复用。
        将return为一个序列,可以直接复用该序列。
    1 def fibonacci(num):
    2     fibs = [0,1]
    3     for i in range(num-2):
    4         fibs.append(fibs[-2]+fibs[-1])   #倒数第二个+倒数第一个数的结果,追加到列表
    5     return(fibs)
    6 fibonacci(5)

    或者

    1 def fab_demo2(max):
    2     a, n, b = 0, 0, 1
    3     list_demo = []
    4     while n < max:
    5         list_demo.append(b)
    6         a, b = b, a + b
    7         n += 1
    8     print(list_demo)
    9     return list_demo
    实现四:
        可以复用了,但是考虑到后期若要存储在list中的数据量过大,比较吃内存浪费资源,应该怎么办呢,
        此时,考虑到利用 iterable 我们可以把 fab 函数改写为一个支持 iterable 的 class
     1 class Fab(object):
     2     def __init__(self,max):
     3         self.max = max
     4         self.n ,self.a ,self.b = 0 ,0 ,1
     5 
     6     def __iter__(self):        #继承object,重写__iter__后,自动调用__next__方法,返回r对象
     7         return self
     8 
     9     def __next__(self):        #此处python2为next,python3为__next__,注意区别
    10         if self.n < self.max:
    11             r = self.b
    12             self.a , self.b = self.b , self.a + self.b
    13             self.n += 1
    14             return r      
    15         raise StopIteration()
    16 #Fab 类通过 next() 不断返回数列的下一个数,内存占用始终为常数:
    17 for i in Fab(5):
    18     print(i)
    19 #或者
    20 print(next(iter(Fab(5)))) 

    实现五

    代码不够简洁,使用yield关键字

     1 def fab_demo4(max):
     2     a,n,b = 0,0,1
     3     while n < max:
     4         yield  b
     5         #print b
     6         a,b = b,a+b
     7         n+=1
     8 print(next(fab_demo4(5)))
     9 for i in fab_demo4(5):
    10     print(i)
     
    仅仅把 print b 改为了 yield b,就在保持简洁性的同时获得了 iterable 的效果
    yield 的作用就是把一个函数变成一个 generator,带有 yield 的函数不再是一个普通函数,Python 解释器会将其视为一个 generator,
    调用 fab(5) 不会执行 fab 函数,而是返回一个 iterable 对象!
    在 for 循环执行时,每次循环都会执行 fab 函数内部的代码,执行到 yield b 时,fab 函数就返回一个迭代值,
    下次迭代时,代码从 yield b 的下一条语句继续执行,而函数的本地变量看起来和上次中断执行前是完全一样的,于是函数继续执行,直到再次遇到 yield。
     
    也可以手动调用 fab(5) 的 next() 方法(因为 fab(5) 是一个 generator 对象,该对象具有 next() 方法)

    我们可以得出以下结论:

    一个带有 yield 的函数就是一个 generator,它和普通函数不同,生成一个 generator 看起来像函数调用,但不会执行任何函数代码,直到对其调用 next()(在 for 循环中会自动调用 next())才开始执行。虽然执行流程仍按函数的流程执行,但每执行到一个 yield 语句就会中断,并返回一个迭代值,下次执行时从 yield 的下一个语句继续执行。看起来就好像一个函数在正常执行的过程中被 yield 中断了数次,每次中断都会通过 yield 返回当前的迭代值。

    yield 的好处是显而易见的,把一个函数改写为一个 generator 就获得了迭代能力,比起用类的实例保存状态来计算下一个 next() 的值,不仅代码简洁,而且执行流程异常清晰。

    如何判断一个函数是否是一个特殊的 generator 函数?可以利用 isgeneratorfunction 判断:

    1 >>> from inspect import isgeneratorfunction
    2 >>> isgeneratorfunction(fab)
    3 True

    要注意区分 fab 和 fab(5),fab 是一个 generator function,而 fab(5) 是调用 fab 返回的一个 generator,好比类的定义和类的实例的区别:

  • 相关阅读:
    Android Studio 编译不通过,报错“找不到org.apache.http
    Android studio中出现非法字符时的部分解决方法
    eclipse项目导入到Android Studio Plugin with id 'android-library' not found
    将Eclipse代码导入到AndroidStudio的两种方式
    eclipse项目迁移到android studio(图文最新版)
    Android studio插件安装
    ViewPager PagerAdapter不更新视图
    Android:可扩展伸缩listview
    Android的崩溃错误报告之ACRA
    Android数据库ORMlite框架04
  • 原文地址:https://www.cnblogs.com/kunpengv5/p/63a628ad1921e2904b3c85bc3303c6ba.html
Copyright © 2020-2023  润新知