Tak wiele pytań tutaj. Widzę co najmniej dwa, może trzy:
- Co robi pop (a, b)? / Dlaczego jest drugi argument?
- Do czego
*args
służy?
Na pierwsze pytanie można znaleźć trywialną odpowiedź w dokumentacji Python Standard Library :
pop (klawisz [, domyślny])
Jeśli klucz znajduje się w słowniku, usuń go i zwróć jego wartość, w przeciwnym razie zwróć wartość domyślną. Jeśli nie podano wartości domyślnej, a klucza nie ma w słowniku, generowany jest błąd KeyError.
Drugie pytanie jest omówione w Python Language Reference :
Jeśli występuje postać „* identifier”, jest ona inicjowana w postaci krotki otrzymującej wszelkie nadmiarowe parametry pozycyjne, domyślnie pustej krotki. Jeśli występuje postać „** identyfikator”, jest on inicjowany w nowym słowniku, który otrzymuje nadmiarowe argumenty słów kluczowych, domyślnie nowy pusty słownik.
Innymi słowy, pop
funkcja przyjmuje co najmniej dwa argumenty. Pierwsze dwa otrzymują nazwy self
i key
; a reszta jest umieszczana w krotce o nazwie args
.
To, co dzieje się w następnej linii, gdy *args
jest przekazywane w wywołaniu, self.data.pop
jest odwrotnością tego - krotka *args
jest rozwijana do parametrów pozycyjnych, które są przekazywane dalej. Jest to wyjaśnione w dokumencie Python Language Reference :
Jeśli wyrażenie składni * pojawia się w wywołaniu funkcji, wyrażenie musi wyliczać na sekwencję. Elementy z tej sekwencji są traktowane tak, jakby były dodatkowymi argumentami pozycyjnymi
Krótko mówiąc, a.pop()
chce być elastyczny i akceptować dowolną liczbę parametrów pozycyjnych, aby mógł przekazać tę nieznaną liczbę parametrów pozycyjnych do self.data.pop()
.
Daje to elastyczność; data
tak się składa, że jest to dict
teraz, więc self.data.pop()
przyjmuje jeden lub dwa parametry; ale jeśli zmieniłeś data
się na typ, który wymagał 19 parametrów dla wywołania self.data.pop()
, nie musiałbyś w ogóle zmieniać klasy a
. Nadal musiałbyś jednak zmienić dowolny kod, który wywołałby a.pop()
przekazanie wymaganych 19 parametrów.
help(b.data.pop)
w REPL.