Per le basi sugli argomenti delle funzioni, vedi il concetto di funzione.
I nomi dei parametri, come i nomi delle variabili, devono iniziare con una lettera o un underscore e possono contenere lettere, underscore o numeri. I nomi dei parametri non devono contenere spazi o segni di punteggiatura.
Gli argomenti posizionali sono valori passati a una funzione nello stesso ordine dei parametri a cui si legano. Facoltativamente, gli argomenti posizionali si possono passare usando il nome del parametro:
def concat(greeting, name):
return f"{greeting}{name}"
# Passing data to the function by position.
print(concat("Hello, ", "Lilly"))
#-> Hello, Lilly
# Passing data to the function using the parameter name.
print(concat(name="Glenn", greeting="Hello, "))
#-> Hello, Glenn
La prima chiamata a concat passa gli argomenti per posizione.
La seconda chiamata a concat passa gli argomenti per nome, il che permette di cambiarne la posizione.
Nota che gli argomenti posizionali non possono seguire argomenti passati per nome (detti anche argomenti keyword. Da non confondere con i parametri variadici posizionali o con **kwargs).
Questo insieme di argomenti:
print(concat(greeting="Hello, ", "Gregor"))
Produce questo errore:
SyntaxError: positional argument follows keyword argument
Per richiedere argomenti esclusivamente posizionali nelle chiamate di funzione, si può usare l'operatore / nell'elenco dei parametri:
# Parameters showing a position-only operator.
def concat(greeting, name, /):
return f"{greeting}{name}"
print(concat("Hello, ", "Ginnie"))
#-> Hello, Ginnie
# Call to the function using keyword arguments.
print(concat(name="Franklin", greeting="Hello, "))
Traceback (most recent call last):
print(concat(name="Franklin", greeting="Hello, "))
TypeError: concat() got some positional-only arguments passed as keyword arguments: 'greeting, name'
Gli argomenti keyword usano il nome del parametro quando si chiama una funzione. Facoltativamente, si possono indicare per posizione:
def concat(greeting, name):
return f"{greeting}{name}"
# Function call using parameter names as argument keywords.
print(concat(name="Eliza", greeting="Hello, "))
#-> Hello, Eliza
# Function call with positional data as arguments.
print(concat("Hello, ", "Tim"))
#-> Hello, Tim
Per richiedere argomenti esclusivamente keyword nelle chiamate di funzione, si può usare l'operatore * nell'elenco dei parametri:
# Function definition requiring keyword-only arguments.
def concat(*, greeting, name):
return f"{greeting}{name}"
# Keyword arguments can be in an arbitrary order.
print(concat(name="Kimmie", greeting="Hello, "))
#-> Hello, Kimmie
# Calling the function with positional data raises an error.
print(concat("Hello, ", "Coleen"))
Traceback (most recent call last):
print(concat("Hello, ", "Coleen"))
TypeError: concat() takes 0 positional arguments but 2 were given
Nell'elenco dei parametri si possono indicare valori predefiniti per uno o più argomenti. Questo permette di chiamare la funzione con meno argomenti, se serve. Si possono sovrascrivere i valori predefiniti chiamando la funzione con un nuovo valore per l'argomento:
# Function with default argument values.
def concat(greeting, name="you", punctuation="!"):
return f"{greeting}, {name}{punctuation}"
print(concat("Hello"))
#-> Hello, you!
# Overriding the default values
print(concat("Hello", name="Polly", punctuation="."))
#-> Hello, Polly.
Gli argomenti possono essere posizionali o keyword se nella definizione dei parametri non si usa né l'operatore / né l'operatore *.
In alternativa, gli argomenti posizionali-o-keyword si possono collocare tra i parametri esclusivamente posizionali a sinistra e i parametri esclusivamente keyword a destra:
# Position-only argument followed by position-or-keyword, followed by keyword-only.
def concat(greeting, /, name, *, ending):
return f"{greeting}{name}{ending}"
print(concat("Hello, ", "Mark", ending="!"))
#-> Hello, Mark!
print(concat("Hello, ", name="Rachel", ending="!"))
#-> Hello, Rachel!
print(concat(greeting="Hello, ", name="JoJo", ending="!"))
Traceback (most recent call last):
print(concat(greeting="Hello, ", name="JoJo", ending="!"))
TypeError: concat() got some positional-only arguments passed as keyword arguments: 'greeting'
*argsGli esempi di codice usano spesso una definizione di funzione simile a questa:
def my_function(*args, **kwargs):
# code snipped
*args è un nome in due parti che rappresenta una tuple con un numero indefinito di argomenti posizionali separati, detto anche variadic argument.
args è il nome dato alla tuple di argomenti, ma potrebbe essere qualsiasi altro nome Python valido, come my_args, arguments, ecc.
Il * è l'operatore che trasforma il gruppo di argomenti separati in una tuple.
Se ti è mai capitato di spacchettare una tupla, potresti trovare confuso il * in *args.
Il * in una definizione di parametro, invece di spacchettare una tupla, converte uno o più argomenti posizionali in una tupla.
Diciamo che l'operatore * è sovraccaricato, perché si comporta in modo diverso in contesti diversi.
Per esempio, * si usa per la moltiplicazione, per lo spacchettamento e per definire un numero arbitrario di parametri posizionali.
Dato che una tuple si può iterare, args si può passare a qualsiasi altra funzione che accetta un iterabile.
Anche se *args si trova spesso accanto a **kwargs, non è obbligatorio:
def add(*args):
# args is passed to the sum function, which iterates over it.
return sum(args)
print(add(1, 2, 3))
#-> 6
Se *args segue uno o più argomenti posizionali, allora *args conterrà ciò che resta dopo gli argomenti posizionali:
def add(first, *args):
# first will be 1, leaving the values 2 and 3 in *args
return first + sum(args)
print(add(1, 2, 3))
#-> 6
Se uno o più argomenti predefiniti sono definiti dopo *args, restano separati dai valori di *args:
def add(first, *args, last=0):
return first + sum(args) + last
print(add(1, 2, 3))
#-> 6
print(add(1, 2, 3, last=4))
#-> 10
# This uses the unpacking operator * to separate the list elements into positional arguments.
# It does not have the same behavior as the * (packing) in *args.
print(add(*[1, 2, 3]))
#-> 6
Nota che quando un argomento è già dentro un iterable (come una tuple o una list), va spacchettato prima di passarlo a una funzione che accetta un numero arbitrario di argomenti separati.
Questo si ottiene usando *, l'operatore di spacchettamento.
In questo contesto, * spacchetta il contenitore nei suoi elementi separati, che poi *args trasforma in una tuple.
Quando ci sono solo argomenti posizionali, l'operazione di spacchettamento deve produrre lo stesso numero di argomenti dei parametri formali definiti.
Senza spacchettare la lista passata ad add, il programma darebbe errore:
def add(first, *args, last=0):
return first + sum(args) + last
print(add([1, 2, 3]))
Traceback (most recent call last):
print(add([1, 2, 3]))
return first + sum(args) + last
TypeError: can only concatenate list (not "int") to list
**kwargs**kwargs è un nome in due parti che rappresenta un numero indefinito di argomenti separati come coppie chiave-valore.
kwargs è il nome del gruppo di argomenti e potrebbe essere qualsiasi altro nome, come my_args, arguments, ecc.
Il ** trasforma il gruppo di argomenti con nome in un dictionary di coppie {argument name: argument value}.
Dato che un dizionario si può iterare, kwargs si può passare a qualsiasi altra funzione che accetta un iterabile.
Anche se **kwargs si trova spesso accanto a *args, non è obbligatorio:
def add(**kwargs):
return sum(kwargs.values())
print(add(one=1, two=2, three=3))
#-> 6
Nota che si chiama il metodo dict.values() per iterare sui values del dizionario kwargs.
Quando si itera su un dizionario, il comportamento predefinito è iterare sulle keys, quindi dict.values() va specificato esplicitamente:
def concat(**kwargs):
# Join concatenates the tuples from `kwargs.items()`
return " ".join((str(item) for item in kwargs.items()))
print(concat(one=1, two=2, three=3))
#-> ('one', 1) ('two', 2) ('three', 3)