首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >动态规划- Fibonacci

动态规划- Fibonacci
EN

Stack Overflow用户
提问于 2015-12-03 00:05:42
回答 2查看 7.7K关注 0票数 4

因此,基本上,我是一个学习程序员,这周我被介绍了动态编程。我们的任务是使用动态规划找到Fibonacci序列。这个伪代码显然是在一个函数中提供的:

代码语言:javascript
复制
init table to 0s
if n ≤ 1
   return n
else
   if table[n-1] = 0
      table[n-1] = dpFib(n-1)
   if table[n-2] = 0
      table[n-2] = dpFib(n-2)
   table[n] = table[n-1] + table[n-2]
return table[n]

其中大部分很容易更改为代码,但我不知道如何初始化0的表。我知道它应该是一个列表,但是我不确定它应该在函数内部还是外部,或者我应该用多少个零来初始化它。这就是我写的,没有什么复杂的:

代码语言:javascript
复制
def dynamicFibo(n):
   # initialise table of 0s
   #base case
   if n <= 1:
       return n
   #recursive case
   else:
       if table[n-1] ==  0:
           table[n-1] = dynamicFibo(n-1)

       if table[n-2] ==  0:
           table[n-2] = dynamicFibo(n-2)

       table[n] = table[n-2] + table[n-2]
   return table[n]

如果有人能给我指路,我会很感激的。而且,总的来说,我很难理解动态规划的基础,所以如果有任何好的资源,你可以建议我很高兴,或者即使你能给出一个很好的解释。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2015-12-03 00:32:51

您可以使用以下方法初始化table

代码语言:javascript
复制
table = [0 for _ in range(n+1)]

因为您希望在表中至少包含n+1项以允许访问table[n] (请记住列表是零索引的,因此nth项可以用(n-1)访问)

但是,您可能希望确保每次都不会创建新的列表,因为这将违背动态编程的目的。因此,您可以将table作为我所称的“不可见的”参数,即在每次递归调用时使用的具有默认参数的参数。然后,您的函数将如下所示:

代码语言:javascript
复制
>>> def dynamicFibo(n,table = []):
   while len(table) < n+1: table.append(0) #this does the same thing except it doesn't change the reference to `table`
   #base case
   if n <= 1:
       return n
   #recursive case
   else:
       if table[n-1] ==  0:
           table[n-1] = dynamicFibo(n-1)

       if table[n-2] ==  0:
           table[n-2] = dynamicFibo(n-2)

       table[n] = table[n-2] + table[n-1]
   return table[n]
>>> dynamicFibo(12)
144
>>> dynamicFibo(300)
222232244629420445529739893461909967206666939096499764990979600

参考文献

正如您所看到的,我使用了while循环,而不是列表理解。这本质上是一样的,除非我们不能更改table的引用,否则递归调用每次都会创建一个新表,除非您将它作为参数传递进来。这还允许表根据需要展开,如果您多次使用递增的数字调用dynamicFibo,但保留所有旧的数字。通过在函数中添加一个print(table)行可以清楚地看到这一点:

代码语言:javascript
复制
>>> dynamicFibo(12)
[0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
[0, 1, 1, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0]
[0, 1, 1, 2, 3, 0, 0, 0, 0, 0, 0, 0, 0]
[0, 1, 1, 2, 3, 5, 0, 0, 0, 0, 0, 0, 0]
[0, 1, 1, 2, 3, 5, 8, 0, 0, 0, 0, 0, 0]
[0, 1, 1, 2, 3, 5, 8, 13, 0, 0, 0, 0, 0]
[0, 1, 1, 2, 3, 5, 8, 13, 21, 0, 0, 0, 0]
[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 0, 0, 0]
[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 0, 0]
[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 0]
[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144]
144
>>> dynamicFibo(14)
[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 0]
[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 377]
377

我在print(table)之前添加了return table[n]

票数 7
EN

Stack Overflow用户

发布于 2020-05-19 16:53:14

有一个简单的解决方案对每个人都有效..。

代码语言:javascript
复制
def fib(n):
    table = []
    table.append(0)
    table.append(1)
    for i in range(2, n+1):
        table.append(table[i-1] + table[i-2])
    return(table[n])
票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/34055512

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档