I den enorme verden av Python-programmering er det et sett med funksjoner som ofte går ubemerket av nybegynnere, men som likevel har betydelig betydning i språkets økosystem.
Magiske metoder er et sett med forhåndsmetoderdefinites i Python som gir spesielle syntaktiske funksjoner. De er lett å kjenne igjen på deres doble bindestreker i begynnelsen og slutten, som __init__, __call__, __len__
… etc.
Magiske metoder lar tilpassede objekter oppføre seg på samme måte som innebygde Python-typer.
I denne artikkelen vil vi fokusere på de kraftige dunder-funksjonene. Vi vil utforske formålet deres og diskutere bruken.
Enten du er en Python-nybegynner eller en erfaren programmerer, har denne artikkelen som mål å gi deg en omfattende forståelse av Dunder-funksjoner, noe som gjør Python-kodingsopplevelsen mer effektiv og fornøyelig.
Husk at magien til Python ikke bare ligger i dens enkelhet og allsidighet, men også i dens kraftige funksjoner som Dunder-funksjoner.
Kanskje den mest grunnleggende dunder-funksjonen av alle. Dette er den magiske metoden som Python automatisk kaller når vi lager (eller som navnet antyder, initialiserer) et nytt objekt.__init__
klasse pizza:
def __init__(selv, størrelse, pålegg):
self.size = størrelse
self.toppings = toppings
# La oss nå lage en pizza
min_pizza = Pizza('stor', ['pepperoni', 'sopp'])
print(my_pizza.size) # Dette vil skrive ut: large
print(my_pizza.toppings) # Dette vil skrive ut: ['pepperoni', 'sopp']
I dette eksemplet opprettes en klasse kalt Pizza. Vi setter opp __init__-funksjonen vår til å inkludere parametere som skal spesifiseres ved initialiseringstidspunktet, og setter dem som egenskaper for vårt egendefinerte objekt.
Her brukes den til å representere forekomsten av klassen. Så når vi skriver self.size = size, sier vi: "Hei, dette pizzaobjektet har en attributtstørrelse size
, og jeg vil at den skal ha den størrelsen jeg oppga da jeg opprettet objektet».
Dette er Pythons magiske metode som lar oss definish en beskrivelse for vår egendefinerte vare.
Når du skriver ut et objekt eller konverterer det til en streng ved hjelp av str()
, Python sjekk om du har defiJeg har kommet opp med en metode __str__
for det objektets klasse.
Hvis ja, bruk den metoden til å konvertere objektet til en streng.
Vi kan utvide pizzaeksemplet vårt til å inkludere en funksjon __str__
som følger:
klasse Pizza: def __init__(selv, størrelse, pålegg): self.size = størrelse self.toppings = toppings def __str__(self): return f"A {self.size} pizza med {', '.join(self.toppings )}" my_pizza = Pizza('stor', ['pepperoni', 'sopp']) print(min_pizza) # Dette vil skrive ut: En stor pizza med pepperoni, sopp
__repr__
__str__-funksjonen er mer en uformell måte å beskrive egenskapene til et objekt på. På den annen side brukes __repr__ for å gi en mer formell, detaljert og entydig beskrivelse av det tilpassede objektet.
Hvis du ringer repr()
på et objekt eller du bare skriver inn objektnavnet i konsollen, vil Python se etter en metode __repr__
.
Se __str__
ingen definite, vil Python bruke __repr__
som en sikkerhetskopi når du prøver å skrive ut objektet eller konvertere det til en streng. Så det er ofte en god idé defifullfør minst __repr__
, selv om du ikke gjør det defikommer ut __str__
.
Her er hvordan vi kunne defibli ferdig __repr__
for vårt pizzaeksempel:
klasse pizza:
def __init__(selv, størrelse, pålegg):
self.size = størrelse
self.toppings = toppings
def __repr__(selv):
return f"Pizza('{self.size}', {self.toppings})"
min_pizza = Pizza('stor', ['pepperoni', 'sopp'])
print(repr(min_pizza)) # Dette vil skrive ut: Pizza('stor', ['pepperoni', 'sopp'])
__repr__
gir deg en streng som du kan kjøre som en Python-kommando for å gjenskape pizzaobjektet, mens __str__
gir deg en mer menneskelig beskrivelse. Jeg håper det hjelper deg med å tygge disse dunder-metodene litt bedre!
I Python vet vi alle at det er mulig å legge til tall ved hjelp av operatoren +
, Som 3 + 5
.
Men hva om vi vil legge til forekomster av et tilpasset objekt?
Dunder-funksjonen __add__
det lar oss gjøre nettopp det. Det gir oss muligheten til definish oppførselen til operatøren +
på våre personlige varer.
Av hensyn til konsistens, la oss anta at vi ønsker det defifullføre oppførselen til +
på pizzaeksemplet vårt. La oss si at når vi legger til to eller flere pizzaer sammen, vil den automatisk kombinere alle påleggene deres. Slik kan det se ut:
klasse pizza:
def __init__(selv, størrelse, pålegg):
self.size = størrelse
self.toppings = toppings
def __add__(selv, annet):
hvis ikke er forekomst (annet, pizza):
raise TypeError("Du kan bare legge til en annen pizza!")
new_toppings = self.toppings + other.toppings
returner pizza(selv.størrelse, nye_pålegg)
# La oss lage to pizzaer
pizza1 = Pizza('stor', ['pepperoni', 'sopp'])
pizza2 = Pizza('stor', ['oliven', 'ananas'])
# Og la oss nå "legge til" dem
kombinert_pizza = pizza1 + pizza2
print(combined_pizza.toppings) # Dette vil skrive ut: ['pepperoni', 'sopp', 'oliven', 'ananas']
På samme måte som dunder __add__
, det kan vi også defifullføre andre aritmetiske funksjoner som f.eks __sub__
(ved subtraksjon ved hjelp av operatoren -
) Og __mul__
(for multiplikasjon ved hjelp av operatoren *
).
Denne dundermetoden lar oss defifullføre hva funksjonen len()
må returnere for våre tilpassede varer.
Python bruker len()
for å få lengden eller størrelsen på en datastruktur, for eksempel en liste eller streng.
I sammenheng med vårt eksempel kan vi si at "lengden" på en pizza er antall pålegg den har. Slik kan vi implementere det:
klasse pizza:
def __init__(selv, størrelse, pålegg):
self.size = størrelse
self.toppings = toppings
def __len__(selv):
return len(self.toppings)
# La oss lage en pizza
my_pizza = Pizza('stor', ['pepperoni', 'sopp', 'oliven'])
print(len(my_pizza)) # Dette vil skrive ut: 3
I __len__-metoden returnerer vi kun lengden på listen toppings
. Nå, len(my_pizza)
den vil fortelle oss hvor mange pålegg som er på den my_pizza
.
Denne dunder-metoden gjør at objekter kan itereres, det vil si at den kan brukes i en for-løkke.
For å gjøre dette må vi også defifullfør funksjonen __next__
, Dette brukes til definish atferden som skal returnere neste verdi i iterasjonen. Det skal også signalisere det iterable på hendelsen at det ikke er flere elementer i sekvensen. Dette oppnår vi vanligvis ved å gjøre et unntak StopIteration
.
For pizzaeksemplet vårt, la oss si at vi ønsker å gjenta toppingene. Vi kan gjøre pizzaklassen vår gjentakelig definendo en metode __iter__
:
klasse pizza:
def __init__(selv, størrelse, pålegg):
self.size = størrelse
self.toppings = toppings
def __iter__(selv):
selv.n = 0
returnere selv
def __neste__(selv):
if self.n < len(self.toppings):
resultat = self.toppings[self.n]
self.n += 1
returnere resultat
ellers:
heve StopIteration
# La oss lage en pizza
my_pizza = Pizza('stor', ['pepperoni', 'sopp', 'oliven'])
# Og la oss nå iterere over det
for topping i min_pizza:
print (topping)
I dette tilfellet for loop-anrop __iter__
, som initialiserer en teller (self.n)
og returnerer selve pizzaobjektet (self)
.
Deretter for loop-anrop __next__
for å få hver pålegg etter tur.
Når __next__
returnerte alle krydder, StopIteration
det gir et unntak, og for-løkken vet nå at det ikke er flere pålegg og vil derfor avbryte iterasjonsprosessen.
Ercole Palmeri
Sist mandag kunngjorde Financial Times en avtale med OpenAI. FT lisensierer sin journalistikk i verdensklasse...
Millioner av mennesker betaler for strømmetjenester og betaler månedlige abonnementsavgifter. Det er vanlig oppfatning at du...
Coveware by Veeam vil fortsette å tilby responstjenester for cyberutpressing. Coveware vil tilby kriminaltekniske og utbedringsmuligheter...
Prediktivt vedlikehold revolusjonerer olje- og gasssektoren, med en innovativ og proaktiv tilnærming til anleggsledelse...