Följande funktionsargument är troligen de vanligaste argumenten som du inte förstår när du tittar på Python-kod och frågar dig: ”Vad är det här?
*args
**kwargs
Ett obegränsat antal argument (argument med variabel längd) kan anges genom att lägga till en asterisk till argumentet i funktionsdefinitionen på följande sätt
*
**
Namnen *args,**kwargs används ofta som en konvention. Andra namn är dock acceptabla så länge * och ** står i början. I följande exempelkod används namnen *args,**kwargs.
Nedan följer en beskrivning av följande uppgifter.
*args
:Accepterar flera argument som en tupel.**kwargs
:Accepterar flera nyckelordsargument som en ordbok
*args: Accepterar flera argument som en tupel.
Ett godtyckligt antal argument kan anges genom att definiera argumenten med *, som i *args.
def my_sum(*args):
return sum(args)
print(my_sum(1, 2, 3, 4))
# 10
print(my_sum(1, 2, 3, 4, 5, 6, 7, 8))
# 36
Flera argument tas emot som en tupel i funktionen. I exemplet får funktionen sum() en tupel för att beräkna summan.
def my_sum2(*args):
print('args: ', args)
print('type: ', type(args))
print('sum : ', sum(args))
my_sum2(1, 2, 3, 4)
# args: (1, 2, 3, 4)
# type: <class 'tuple'>
# sum : 10
Det kan också kombineras med ett positionsargument.
Värdet som anges efter (till höger om) det positionella argumentet skickas till args som en tupel. Om det bara finns ett positionsargument är det en tom tupel.
def func_args(arg1, arg2, *args):
print('arg1: ', arg1)
print('arg2: ', arg2)
print('args: ', args)
func_args(0, 1, 2, 3, 4)
# arg1: 0
# arg2: 1
# args: (2, 3, 4)
func_args(0, 1)
# arg1: 0
# arg2: 1
# args: ()
Argument markerade med * kan definieras först. I detta fall måste dock argument som definieras senare än *args anges i nyckelordsform. Nyckelordsformatet är för övrigt formen ”argumentnamn = värde”.
Det sista värdet överförs inte automatiskt till positionsargumentet. Om det inte anges som ett nyckelordsargument uppstår därför ett TypeError-fel.
def func_args2(arg1, *args, arg2):
print('arg1: ', arg1)
print('arg2: ', arg2)
print('args: ', args)
# func_args2(0, 1, 2, 3, 4)
# TypeError: func_args2() missing 1 required keyword-only argument: 'arg2'
func_args2(0, 1, 2, 3, arg2=4)
# arg1: 0
# arg2: 4
# args: (1, 2, 3)
Om endast *-argument anges måste efterföljande argument alltid anges som nyckelordsargument.(keyword-only argument
)
def func_args_kw_only(arg1, *, arg2):
print('arg1: ', arg1)
print('arg2: ', arg2)
# func_args_kw_only(100, 200)
# TypeError: func_args_kw_only() takes 1 positional argument but 2 were given
func_args_kw_only(100, arg2=200)
# arg1: 100
# arg2: 200
**kwargs: Accepterar flera nyckelordsargument som en ordbok
Ett godtyckligt antal nyckelordsargument kan anges genom att definiera argumenten med ,** som i **kwargs.
I funktionen tas argumentets namn emot som en ordbok vars nyckel är key och vars värde är value.
def func_kwargs(**kwargs):
print('kwargs: ', kwargs)
print('type: ', type(kwargs))
func_kwargs(key1=1, key2=2, key3=3)
# kwargs: {'key1': 1, 'key2': 2, 'key3': 3}
# type: <class 'dict'>
Det kan också användas i samband med en argumentation för en ståndpunkt.
def func_kwargs_positional(arg1, arg2, **kwargs):
print('arg1: ', arg1)
print('arg2: ', arg2)
print('kwargs: ', kwargs)
func_kwargs_positional(0, 1, key1=1)
# arg1: 0
# arg2: 1
# kwargs: {'key1': 1}
Genom att ange ordboksobjektet med ** som ett argument när du anropar funktionen är det möjligt att expandera det och skicka det som respektive argument.
d = {'key1': 1, 'key2': 2, 'arg1': 100, 'arg2': 200}
func_kwargs_positional(**d)
# arg1: 100
# arg2: 200
# kwargs: {'key1': 1, 'key2': 2}
Argument markerade med ** får endast definieras i slutet av argumentet. Att definiera ett annat argument efter argumentet markerat med ** resulterar i ett SyntaxError-fel.
# def func_kwargs_error(**kwargs, arg):
# print(kwargs)
# SyntaxError: invalid syntax