python,ipython运行交互式脚本
我有一个名为“poc.py”的脚本,它接受一个位置命令行参数“inputfile.txt”。poc.py脚本使用python,ipython运行交互式脚本,python,pandas,ipython,Python,Pandas,Ipython,我有一个名为“poc.py”的脚本,它接受一个位置命令行参数“inputfile.txt”。poc.py脚本使用argparse处理位置命令行参数,然后将args dict传递给main()。一旦进入main(),我就读取输入文件,进行一些处理,创建一个pandas数据帧,最后绘制数据。我在操作数据帧和控制结果图的精确格式方面遇到困难,因此我想尝试ipython以交互方式探索这一点,看看是否能够更好地掌握处理pandas/matplotlib的“pythonic”方法 所以我尝试使用ipytho
argparse
处理位置命令行参数,然后将args dict传递给main()
。一旦进入main()
,我就读取输入文件,进行一些处理,创建一个pandas数据帧,最后绘制数据。我在操作数据帧和控制结果图的精确格式方面遇到困难,因此我想尝试ipython以交互方式探索这一点,看看是否能够更好地掌握处理pandas/matplotlib的“pythonic”方法
所以我尝试使用ipython并运行脚本,但我无法让ipython保留脚本的名称空间
我试过这个:
$ ipython --pylab -i poc.py inputfile.txt
它可以很好地运行我的脚本,并显示绘图(即使没有阻塞plt.show()
调用),但是当脚本完成时,ipython who
和whos
命令说交互式命名空间为空。同样,如果我首先进入ipython外壳,然后执行以下操作:
In [2]: run poc.py inputfile.txt
当脚本完成时(同样,大量的输出和绘图显示),我得到了相同的结果:一个空的交互式名称空间
在理解如何运行外部脚本并使用ipython以交互方式浏览脚本中的数据/对象方面,我缺少什么
下面是如何设置我的脚本(poc.py
)的一个简单示例:
import numpy as np
import matplotlib as plt
import pandas as pd
# etc ...more libraries and custom functions here...
def main(args):
data = np.genfromtxt(args.inputfile)
# (omitted)...more data processing / manipulation...
pdata = pd.DataFrame(data)
# (omitted)...more data processing / manipulation...
plt.plot(pdata)
# (omitted)...some formatting of the matplotlib/axes/figure objects
plt.show()
if __name__ == '__main__':
parser = argparse.ArgumentParser(description='''some program...''')
parser.add_argument('inputfile', help='path to input file')
args = parser.parse_args()
main(args)
这里的问题是data
和pdata
不在脚本的命名空间中;它们位于已经运行并完成的函数的本地命名空间中
如果你想在事后检查它们,你需要把它们存放在某个地方。例如:
# ...
plt.show()
return data, pdata, plt
if __name__ == '__main__':
parser = argparse.ArgumentParser(description='''some program...''')
parser.add_argument('inputfile', help='path to input file')
args = parser.parse_args()
data, pdata, plt = main(args)
(或者,您可以将main的所有变量设置为全局变量,但这种方式看起来更简洁。)
现在,脚本的名称空间包括名为data
、pdata
和plt
的变量,这些变量具有所需的值。另外,您可以再次调用main
,并将另一个文件传递给它,然后从该文件中获取值。在这里回答我自己的问题。我知道这可能是一个评论,但我认为描述需要一个独立的答案
基本上,在花了一些时间来理解大家提到的关于我的变量超出范围的问题,以及处理这些问题的不同方法之后,我找到了另一个适合我的解决方案。我最终使用了IPython的embed()函数。对于调试过程,我要添加
...
from IPython import embed
embed()
...
在脚本中我想停下来四处看看的地方。一旦落入IPython壳中,我就可以研究可变尺寸,并进行操纵实验。当我找到我想要的组合时,我会复制命令,退出交互式解释器并修改脚本。这对我起作用的原因是它不涉及修改程序的结构来获取调试信息。您的模块的名称空间中没有任何内容,只有np
、plt
、pd
、main
、解析器
和args
。特别是,data
和pdata
是已经完成的函数调用的局部变量。您的问题是因为您无法在不重新导入的情况下查看pd
,还是缺少args
?或者你看不到数据
和数据
?我想看数据
和数据
。所以我想我想要的是在退出main()
之前让IPython“停止”?好吧,如果Python在执行main
之前停止,那么这些值甚至还不会被创建。但是如果这是您想要的,那很简单:只需导入模块而不是运行它;然后你可以在空闲时调用main
(并放入调试器断点或其他任何东西)。另一方面,如果你想main
实际运行,但留下它的值,它必须要么使变量global
,要么最好是返回它们,让你的顶级脚本存储它们。这正是我想要的。令人惊讶的是,在IPython的命令行标志下,这个用例是不可能的。