【问题标题】:Memoization in recursive function递归函数中的记忆
【发布时间】:2012-11-26 12:15:36
【问题描述】:

我遇到了一个奇怪的现象:

我写了一个代码来计算“加泰罗尼亚数字”,这很有效,但现在我正在尝试通过使用记忆字典(称为双加泰罗尼亚语)来提高运行时间:

dicatalan = {} 
def catalan(n):
    if n == 0:
        return 1
    else: 
        res = 0
        if n not in dicatalan:
            for i in range(n):
                res += catalan(i) * catalan(n - i - 1)
            dicatalan[n] = res
            print ("dicatalan is", dicatalan)
    return dicatalan[n]

这是一个问题——在 eclipse 中——Pydev——n=1 代码运行一半并按预期打印:“dicatalan is 1:1”然后神秘地停止,但在 IDLE 中相同的代码打印“dicatalan is 0:1” .

无论如何,在尝试打印以后的双加泰罗尼亚语时,我收到了 {}。

怎么可能?代码中发生了什么? 运行调试器被证明是徒劳的。

有什么想法可以让 dict 正常工作吗?

【问题讨论】:

  • 我认为您从未在双加泰罗尼亚语中存储 0,这是导致更多问题的原因。
  • 在缩进代码后,它在这里工作得很好(字典内容、打印、结果)。在我对您的帖子进行编辑后,您能否确认您的缩进是相同的?
  • @mmgp 我可以确认代码对我来说可以正常工作:)
  • 这对我也很有效。有一个库可以在 functools 中进行记忆:stackoverflow.com/a/12562777/1240268

标签: python dictionary memoization


【解决方案1】:

对我来说也很好,我冒昧地简化了你的代码:

def catalan(n, memo={0: 1}):
  if n not in memo:
    memo[n] = sum((catalan(i) * catalan(n - i - 1)) for i in range(n))
  return memo[n]

【讨论】:

  • 大家好,我现在觉得很有趣。可能问题源于错误的语法(dicatalan [(n)])......复制缩进代码后(感谢mmgp) - 现在它也适用于我。 sega_sai - 你是对的,但它并没有造成应有的结果...... wim - 非常优雅,可爱的一个。非常感谢大家。
  • @user1868486 只是一个澄清:dicatalan[(n)] 完全等同于dicatalan[n],所以这不是导致问题的原因。另外,我没有进行此更改,它是由其他人进一步编辑的。但是我将缩进更改为对我来说似乎合理的内容,因此如果您仍有原始代码,可以将其与我的缩进编辑进行比较(您可以通过单击底部的“编辑 X 小时前”链接来检查所做的编辑你的帖子)。
猜你喜欢
  • 1970-01-01
  • 2014-10-31
  • 2012-04-01
  • 1970-01-01
  • 1970-01-01
  • 2010-09-20
  • 2021-11-17
  • 1970-01-01
  • 2014-01-29
相关资源
最近更新 更多