Python:如何检查是否设置了可选的函数参数
在Python中有一种简单的方法来检查可选参数的值是否来自其默认值,或者是因为用户在函数调用中显式地设置了值吗?
不是真的。 标准的方法是使用用户不需要传递的默认值,例如object
实例:
DEFAULT = object() def foo(param=DEFAULT): if param is DEFAULT: ...
通常你可以使用None
作为默认值,如果它没有意义,作为用户想要通过的值。
另一种方法是使用kwargs
:
def foo(**kwargs): if 'param' in kwargs: param = kwargs['param'] else: ...
但是这太冗长了,使你的函数更难使用,因为它的文档不会自动包含param
参数。
下面的函数装饰器explicit_checker
,明确给出了所有参数的一组参数名称。 它将结果作为一个额外的参数( explicit_params
)添加到函数中。 只需'a' in explicit_params
执行'a' in explicit_params
来检查参数a
是否明确给定。
def explicit_checker(f): varnames = f.func_code.co_varnames def wrapper(*a, **kw): kw['explicit_params'] = set(list(varnames[:len(a)]) + kw.keys()) return f(*a, **kw) return wrapper @explicit_checker def my_function(a, b=0, c=1, explicit_params=None): print a, b, c, explicit_params if 'b' in explicit_params: pass # Do whatever you want my_function(1) my_function(1, 0) my_function(1, c=1)
我有时使用通用唯一string(如UUID)。
import uuid DEFAULT = uuid.uuid4() def foo(arg=DEFAULT): if arg is DEFAULT: # it was not passed in else: # it was passed in
这样,没有用户甚至可以猜测默认值,如果他们尝试了,我可以非常有arg
看到,当我看到arg
值时,它没有被传入。
我同意波动的评论。 但是你可以通过以下方式检查:
def function(arg1,...,**optional): if 'optional_arg' in optional: # user has set 'optional_arg' else: # user has not set 'optional_arg' optional['optional_arg'] = optional_arg_default_value # set default
一个奇怪的方法是:
class CheckerFunction(object): def __init__(self, function, **defaults): self.function = function self.defaults = defaults def __call__(self, **kwargs): for key in self.defaults: if(key in kwargs): if(kwargs[key] == self.defaults[key]): print 'passed default' else: print 'passed different' else: print 'not passed' kwargs[key] = self.defaults[key] return self.function(**kwargs) def f(a): print a check_f = CheckerFunction(f, a='z') check_f(a='z') check_f(a='b') check_f()
哪些产出:
passed default z passed different b not passed z
正如我所说,现在这是非常怪异的,但它做的工作。 然而,这是相当难读的,与ecatmur的build议类似,不会自动logging。