Определить, был ли передан именованный параметр
-
05-07-2019 - |
Вопрос
Я хотел бы знать, можно ли определить, был ли передан в Python параметр функции со значением по умолчанию.Например, как работает dict.pop?
>>> {}.pop('test')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
KeyError: 'pop(): dictionary is empty'
>>> {}.pop('test',None)
>>> {}.pop('test',3)
3
>>> {}.pop('test',NotImplemented)
NotImplemented
Как метод pop определяет, что в первый раз не было передано возвращаемое значение по умолчанию?Это то, что можно сделать только на C?
Спасибо
Решение
Я думаю, вы имеете в виду «аргумент ключевого слова», когда говорите «именованный параметр». dict.pop()
не принимает аргумент ключевого слова, поэтому эта часть вопроса является спорной.
>>> {}.pop('test', d=None)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: pop() takes no keyword arguments
Тем не менее, способ определить, был ли предоставлен аргумент, заключается в использовании *args
или **kwargs
синтаксис.Например:
def foo(first, *rest):
if len(rest) > 1:
raise TypeError("foo() expected at most 2 arguments, got %d"
% (len(rest) + 1))
print 'first =', first
if rest:
print 'second =', rest[0]
После некоторой работы и использования **kwargs
Синтаксис также позволяет полностью эмулировать соглашение о вызовах Python, где аргументы могут быть предоставлены либо по позиции, либо по имени, а аргументы, предоставленные несколько раз (по позиции и имени), вызывают ошибку.
Другие советы
Соглашение часто используется arg=None
и использовать
def foo(arg=None):
if arg is None:
arg = "default value"
# other stuff
# ...
чтобы проверить, пройдено оно или нет.Разрешение пользователю пройти None
, что будет интерпретировано так, как если бы аргумент был нет прошедший.
Вы можете сделать это следующим образом:
def isdefarg(*args):
if len(args) > 0:
print len(args), "arguments"
else:
print "no arguments"
isdefarg()
isdefarg(None)
isdefarg(5, 7)
См. документацию Python на звонки для полной информации.
def f(one, two=2):
print "I wonder if", two, "has been passed or not..."
f(1, 2)
Если это точное значение вашего вопроса, я думаю, что невозможно отличить 2, которая была в значении по умолчанию, от 2, которая была передана.Я не нашел, как осуществить такое различие даже в осмотреть модуль.
Я не уверен, что полностью понимаю, чего вы хотите;однако:
def fun(arg=Ellipsis):
if arg is Ellipsis:
print "No arg provided"
else:
print "arg provided:", repr(arg)
это делает то, что ты хочешь?Если нет, то, как предлагали другие, вам следует объявить свою функцию с помощью *args, **kwargs
синтаксис и проверьте словарь kwargs на наличие параметра.