假设我有一个如下定义的Python函数:

def foo(arg1,arg2):
    #do something with args
    a = arg1 + arg2
    return a

我可以使用foo.func_name获取函数的名称。我如何通过编程获得它的源代码,就像我上面键入的那样?


当前回答

总结一下:

import inspect
print( "".join(inspect.getsourcelines(foo)[0]))

其他回答

拉法łDowgird朋友与答案:

我相信,如果函数是从字符串、流或从编译文件导入的,那么你就不能检索它的源代码。

但是,可以检索从字符串编译的函数的源代码,前提是编译代码还向lineecache添加了一个条目。缓存dict类型:

import linecache
import inspect

script = '''
def add_nums(a, b):
    return a + b
'''

bytecode = compile(script, 'unique_filename', 'exec')
tmp = {}
eval(bytecode, {}, tmp)
add_nums = tmp["add_nums"]

linecache.cache['unique_filename'] = (
    len(script),
    None,
    script.splitlines(True),
    'unique_filename',
)

print(inspect.getsource(add_nums))

# prints:
# """
# def add_nums(a, b):
#    return a + b
# """

这就是attrs库如何自动为类创建各种方法,给定一组类期望初始化的属性。点击这里查看他们的源代码。正如源代码所解释的,这是一个主要用于使调试器(如PDB)能够逐级遍历代码的特性。

如果函数来自文件系统中可用的源文件,那么inspect.getsource(foo)可能会有帮助:

如果foo被定义为:

def foo(arg1,arg2):         
    #do something with args 
    a = arg1 + arg2         
    return a  

然后:

import inspect
lines = inspect.getsource(foo)
print(lines)

返回:

def foo(arg1,arg2):         
    #do something with args 
    a = arg1 + arg2         
    return a                

但我相信,如果函数是从字符串、流或从编译文件导入的,那么你就不能检索它的源代码。

扩展一下runeh的回答:

>>> def foo(a):
...    x = 2
...    return x + a

>>> import inspect

>>> inspect.getsource(foo)
u'def foo(a):\n    x = 2\n    return x + a\n'

print inspect.getsource(foo)
def foo(a):
   x = 2
   return x + a

编辑:正如@0sh指出的那样,这个例子使用ipython工作,而不是纯python。但是,当从源文件导入代码时,在这两种情况下都应该没问题。

只是使用foo??还是? ? foo。

如果你正在使用IPython,那么你需要输入foo??还是? ?Foo来查看完整的源代码。要只看到函数中的文档字符串,请使用foo?或? foo。这也适用于Jupyter笔记本电脑。

In [19]: foo??
Signature: foo(arg1, arg2)
Source:
def foo(arg1,arg2):
    #do something with args
    a = arg1 + arg2
    return a

File:      ~/Desktop/<ipython-input-18-3174e3126506>
Type:      function

你可以使用inspect模块来获得完整的源代码。你必须从inspect模块中使用getsource()方法。例如:

import inspect

def get_my_code():
    x = "abcd"
    return x

print(inspect.getsource(get_my_code))

你可以在下面的链接中查看更多选项。 检索python代码