IPython嵌入式解释器中Fibonacci递归函数报NameError问题
问题原因分析
这个问题的核心是IPython嵌入式解释器的命名空间隔离导致的:
当你执行IPython.embed()启动交互式会话时,这个会话的全局命名空间(也就是你在In [1]中定义函数的环境)和函数内部代码引用的__globals__命名空间并非同一个——函数定义时的__globals__指向的是启动embed()之前的原始全局命名空间(即执行import IPython和IPython.embed()的脚本/环境的全局空间),而非交互式会话的命名空间。
因此,你在交互式会话里定义的fib函数仅存在于IPython交互式会话的命名空间中,但函数内部递归调用的fib会去原始全局命名空间查找,自然找不到对应的名称,最终触发NameError。
验证方式
你可以在交互式会话里打印函数的__globals__来确认这一点:
In [3]: fib.__globals__ is globals() Out[3]: False
返回False就说明两个命名空间确实不是同一个。
解决办法
有两种简单的修复方式:
- 定义函数后,手动把函数绑定到原始全局命名空间:
In [1]: def fib(n): ...: if n <= 1: ...: return n ...: else: ...: return fib(n-1) + fib(n-2) ...: In [2]: import __main__ In [3]: __main__.fib = fib In [4]: fib(2) Out[4]: 1 - 或者直接把函数添加到自身的
__globals__字典中:In [1]: def fib(n): ...: if n <= 1: ...: return n ...: else: ...: return fib(n-1) + fib(n-2) ...: In [2]: fib.__globals__['fib'] = fib In [3]: fib(2) Out[3]: 1
内容的提问来源于stack exchange,提问作者noob overflow
相关产品推荐
相关产品推荐

