Python 为什么要进口pdb;pdb.set_trace在Spyder中调用不同时会触发两种不同的调试场景?
这是我们的后续问题 为什么Python 为什么要进口pdb;pdb.set_trace在Spyder中调用不同时会触发两种不同的调试场景?,python,debugging,ipython,spyder,Python,Debugging,Ipython,Spyder,这是我们的后续问题 为什么导入pdb;pdb.set_trace在Spyder中以不同方式调用时触发两种不同的调试场景? 下面是针对上面提到的问题编辑的示例代码 代码: def foo(): names = ['A', 'B', 'C'] values = [11,12,13] i = 0 import pdb; pdb.set_trace() for n in names: variable = str(n) + ' = ' + st
导入pdb;pdb.set_trace
在Spyder中以不同方式调用时触发两种不同的调试场景?
下面是针对上面提到的问题编辑的示例代码
代码:
def foo():
names = ['A', 'B', 'C']
values = [11,12,13]
i = 0
import pdb; pdb.set_trace()
for n in names:
variable = str(n) + ' = ' + str(values[i])
print(variable)
i += 1
foo()
Scenario1-运行文件(F5)
,继续执行,直到下一个断点(F12)
和运行当前行(F10)
这个程序运行得很好。让我解释一下,为了上下文:
运行文件(F5)
突出显示第2行:
继续执行继续执行,直到下一个断点(F12)
将您直接带到第8行。还请注意,在下面的屏幕截图中,变量浏览器中填充了变量i
、名称
和值。当您使用运行当前行(F10)
浏览代码的其余部分时,会添加和更新其他变量:
或者您可以继续执行,直到下一个断点(F12)
,然后以这种方式完成过程。执行前一步直到foo()
清除变量资源管理器,在ipdb调试器中打印--Return--,然后退出调试器
我想我每次都应该采用这种方式,但我对Spyder提供的运行代码的其他选项非常感兴趣。我特别喜欢用#%%和Ctrl+Enter来定义和运行单元格
场景2-按住Ctrl键并输入包含整个代码的单元格
单元格内的Ctrl+Enter高亮显示第8行,并填充变量资源管理器:
继续执行继续执行,直到下一个断点(F12)
清除变量资源管理器并像前面一样退出调试器:
这也很好,但我的情况是:
场景3-运行和调试多个单元
当我调试大型数据科学项目的代码片段时,我常常在某个地方定义一些变量,并希望调试在其他地方使用这些变量作为输入的函数。这就是为什么我经常会在下面的情况下结束,我在一个单元格中定义了变量,在另一个单元格中使用相同的变量进行For循环:
包含变量的单元格
包含For循环的单元格
但是按Ctrl+Enter并继续运行当前行(F10)会触发interactiveshell.py
中的混乱情况:
现在,问题是:
这是怎么回事
这能避免吗
为什么不能像这样调试单元格(或突出显示的代码+f9)
谢谢你的建议 (这里是Spyder maintainer)我认为问题在于您试图评估函数范围内的单元格。在本例中,所有变量都是作用域的局部变量,因此您无法对foo
进行分段求值,这就是您试图对单元格执行的操作
为了实现您想要的,您可以使用类来代替。这将允许您将数据保存在类中所有方法共享的变量中,并定义要操作这些数据的函数/方法。类还允许您将数据和函数/方法整齐地封装起来,即不在代码的全局范围内定义
这样,您就可以简单地运行一个单元格,调用您想要调试的方法。在您上面发布的示例中,这将是
# %%
class Foo:
def __init__(self):
self.names = ['A', 'B', 'C']
self.values = [11,12,13]
def manipulation(self):
i = 0
import pdb; pdb.set_trace()
for n in self.names:
variable = str(n) + ' = ' + str(self.values[i])
print(variable)
i += 1
f = Foo()
# %%
f.manipulation()
这使我能够毫无问题地调试操纵
方法的工作