假设函数a_method的定义如下
def a_method(arg1, arg2):
pass
从a_method本身开始,我怎么能得到参数名-例如,作为字符串的元组,如("arg1", "arg2")?
假设函数a_method的定义如下
def a_method(arg1, arg2):
pass
从a_method本身开始,我怎么能得到参数名-例如,作为字符串的元组,如("arg1", "arg2")?
当前回答
在python 3中,下面是将*args和**kwargs放入dict(对于python < 3.6使用OrderedDict来维护dict顺序):
from functools import wraps
def display_param(func):
@wraps(func)
def wrapper(*args, **kwargs):
param = inspect.signature(func).parameters
all_param = {
k: args[n] if n < len(args) else v.default
for n, (k, v) in enumerate(param.items()) if k != 'kwargs'
}
all_param .update(kwargs)
print(all_param)
return func(**all_param)
return wrapper
其他回答
在Python 3中。+有了Signature对象,获得参数名到值之间映射的简单方法就是使用Signature的bind()方法!
例如,这是一个用于打印地图的装饰器:
import inspect
def decorator(f):
def wrapper(*args, **kwargs):
bound_args = inspect.signature(f).bind(*args, **kwargs)
bound_args.apply_defaults()
print(dict(bound_args.arguments))
return f(*args, **kwargs)
return wrapper
@decorator
def foo(x, y, param_with_default="bars", **kwargs):
pass
foo(1, 2, extra="baz")
# This will print: {'kwargs': {'extra': 'baz'}, 'param_with_default': 'bars', 'y': 2, 'x': 1}
这里有一些东西,我认为会为你想要的工作,使用装饰。
class LogWrappedFunction(object):
def __init__(self, function):
self.function = function
def logAndCall(self, *arguments, **namedArguments):
print "Calling %s with arguments %s and named arguments %s" %\
(self.function.func_name, arguments, namedArguments)
self.function.__call__(*arguments, **namedArguments)
def logwrap(function):
return LogWrappedFunction(function).logAndCall
@logwrap
def doSomething(spam, eggs, foo, bar):
print "Doing something totally awesome with %s and %s." % (spam, eggs)
doSomething("beans","rice", foo="wiggity", bar="wack")
运行它,它将产生以下输出:
C:\scripts>python decoratorExample.py
Calling doSomething with arguments ('beans', 'rice') and named arguments {'foo':
'wiggity', 'bar': 'wack'}
Doing something totally awesome with beans and rice.
操作一些函数的参数名称的最简单方法:
parameters_list = list(inspect.signature(self.YOUR_FUNCTION).parameters))
结果:
['YOUR_FUNCTION_parameter_name_0', 'YOUR_FUNCTION_parameter_name_1', ...]
这样做会更容易,因为你得到了具体的一个:
parameters_list = list(inspect.signature(self.YOUR_FUNCTION).parameters)[0]
结果:
'YOUR_FUNCTION_parameter_name_0'
在CPython中,参数的数量是
a_method.func_code.co_argcount
他们的名字在开头
a_method.func_code.co_varnames
这些是CPython的实现细节,所以这可能不适用于Python的其他实现,比如IronPython和Jython。
承认“传递”参数的一种可移植方法是使用func(*args, **kwargs)签名来定义函数。这在matplotlib中被大量使用,其中外层API层将大量关键字参数传递给底层API。
Python 3的版本是:
def _get_args_dict(fn, args, kwargs):
args_names = fn.__code__.co_varnames[:fn.__code__.co_argcount]
return {**dict(zip(args_names, args)), **kwargs}
该方法返回一个包含args和kwargs的字典。