Python, аргументы ключевого слова по умолчанию после позиционных аргументов переменной длины

Я думал, что смогу использовать именованные параметры после позиционных параметров переменной длины в вызове функции в Python 2, но я получаю SyntaxError при импорте класса Python. Я пишу с помощью следующего метода "get", например:

class Foo(object):
    def __init__(self):
        print "You have created a Foo."

    def get(self, *args, raw=False, vars=None):
        print len(args)
        print raw
        print vars

Ошибка выглядит так:

def get(self, *args, raw=False, vars=None):
                     ^
SyntaxError: invalid syntax

Я хотел бы иметь возможность вызывать метод несколькими способами:

f = Foo()
f.get(arg1, arg2)
f.get(arg1, raw=True)
f.get(arg1, arg2, raw=True, vars=something)

и Т. Д.


person jkmacc    schedule 09.05.2011    source источник


Ответы (2)


Это работает, но только в Python 3. См. PEP 3102. Глядя на документы «что нового», кажется, что бэкпорта 2.x нет, так что вам не повезло. Вам придется принять любые аргументы ключевого слова (**kwargs) и вручную проанализировать их. Вы можете использовать d.get(k, default), чтобы получить d[k] или default, если его там нет. Чтобы удалить аргумент из kwargs, например. перед вызовом метода суперкласса используйте d.pop.


Обратите внимание, что в def get(self, *args, raw=False, vars=None): raw=False и vars=None не имеют ничего общего с аргументами ключевого слова. Это значения аргументов по умолчанию. Аргументы со значением по умолчанию могут передаваться позиционно, а аргументы без значения по умолчанию могут передаваться по ключевому слову:

def f(a=1): pass
f(2)  # works, passing a positionally
def f(a): pass
f(a=2)  # works, passing a by keyword

Точно так же не требуется, чтобы аргументы, содержащие только ключевые слова, имели значение по умолчанию. После аргумента *args это то, что помечает их как только ключевые слова, а не наличие значения по умолчанию:

def f(*args, a): pass
# a is a mandatory, keyword-only argument
person Community    schedule 09.05.2011
comment
Спасибо вам и Имрану! Ваш ответ с блоком кода Имрана и предложением строки документации отлично ответил на вопрос. - person jkmacc; 09.05.2011

Синтаксис Python не допускает одновременного использования переменных аргументов в функциях и аргументов ключевого слова со значением по умолчанию. Если вы должны иметь аргументы ключевого слова вместе с произвольным количеством позиционных аргументов, вам также необходимо разрешить произвольное количество аргументов ключевого слова.

Это распространенный шаблон для предоставления значений по умолчанию для аргументов ключевого слова, а также разрешения любого количества позиционных аргументов:

def foo(*args, **kwargs):
   raw = kwargs.pop('raw', False)
   vars = kwargs.pop('vars', None)

Если вы вообще не используете дополнительные аргументы ключевого слова, вам не о чем беспокоиться. Это делает функцию менее самодокументируемой, что можно сделать с помощью правильно написанной строки документации.

person Imran    schedule 09.05.2011