我试图定义一个装饰器,只是在装饰函数f
中添加一个关键字参数。 f
可能包含(位置,关键字等)参数的任意组合。我试过这个:
def capture_wrap(f):
def captured(name=False, *args, **kwargs):
"""name can be False, True or str. if str, then use it as a name."""
print (name, f, args, kwargs)
inner = f(*args, **kwargs)
if name is False:
return inner
elif name is True:
return capture(inner)
else:
return capture(inner, name=name)
return captured
如果我尝试将它与一个接受单个参数的函数一起使用:
@capture_wrap
def any_of(s):
"""s must be in the right format.
See https://docs.python.org/3/library/re.html#regular-expression-syntax ."""
return wrap('[', Dinant(s, escape=False), ']')
0-9A-Fa-f <function any_of at 0x7fb370548a60> () {}
Traceback (most recent call last):
File "./dinant.py", line 222, in <module>
hex = one_or_more(any_of('0-9A-Fa-f'))
File "./dinant.py", line 116, in captured
inner = f(*args, **kwargs)
TypeError: any_of() missing 1 required positional argument: 's'
我收到错误,因为any参数成为name
中的captured()
参数。我该怎么做呢?
答案 0 :(得分:1)
您可以name
一个keyword-only argument来实现这一目标。目前的问题是它是一个位置参数,当你正在进行any_of('foo')
时,'foo'
被传递给name
参数。
def capture_wrap(f):
def captured(*args, name=False, **kwargs):
"""name can be False, True or str. if str, then use it as a name."""
print(name, f, args, kwargs)
inner = f(*args, **kwargs)
return inner
return captured
@capture_wrap
def any_of(s1, s2, s3, **kwargs):
return "I do something"
<强>演示:强>
>>> any_of('0-9A-Fa-f', 1, 2)
False <function any_of at 0x1041daea0> ('0-9A-Fa-f', 1, 2) {}
'I do something'
>>> any_of('0-9A-Fa-f', 2, 3, a=1, b=2, name='some-name')
some-name <function any_of at 0x1041daea0> ('0-9A-Fa-f', 2, 3) {'a': 1, 'b': 2}
'I do something'
答案 1 :(得分:0)
只需传递名称,即调用函数f inner = f(name,* args,** kwargs)