Metodi magici in Python
Questo articolo spiega i metodi magici in Python.
YouTube Video
Metodi magici in Python
I metodi magici (o metodi speciali) in Python sono metodi con un nome speciale usati per fornire alle classi un comportamento unico. Ad esempio, sono caratterizzati dall’essere racchiusi tra due underscore (dunders), come __init__
e __str__
. Per questo motivo sono anche chiamati metodi dunder.
Definendo i metodi magici, puoi personalizzare il comportamento standard delle classi. Ad esempio, definire __add__
ti permette di modificare il comportamento dell’operatore +
.
Metodi magici per l’inizializzazione e la rappresentazione in stringa
__init__
: Metodo di inizializzazione
Il metodo __init__
è un costruttore chiamato automaticamente quando viene creata un’istanza.
1class Person:
2 def __init__(self, name, age):
3 self.name = name
4 self.age = age
5
6person = Person("Alice", 30)
7print(person.name) # Alice
__str__
: Rappresentazione in stringa leggibile
Il metodo __str__
restituisce una rappresentazione in stringa leggibile dall’uomo. Viene chiamato da print()
e str()
.
1class Person:
2 def __init__(self, name):
3 self.name = name
4
5 def __str__(self):
6 return f"Person: {self.name}"
7
8person = Person("Bob")
9print(person) # Person: Bob
__repr__
: Rappresentazione in stringa per il debug
Il metodo __repr__
restituisce una rappresentazione in stringa a fini di debug. Viene utilizzato da repr()
e nella visualizzazione all’interno dell’interprete.
1class Person:
2 def __init__(self, name):
3 self.name = name
4
5 def __repr__(self):
6 return f"Person(name={self.name!r})"
7
8person = Person("Eve")
9print(repr(person)) # Person(name='Eve')
Overloading degli operatori aritmetici
__add__
: Operatore +
Usando i metodi magici, è possibile fare l’overloading degli operatori aritmetici. Ad esempio, il metodo __add__
permette di fare l’overloading dell’operatore +
.
1class Vector:
2 def __init__(self, x, y):
3 self.x = x
4 self.y = y
5
6 def __add__(self, other):
7 return Vector(self.x + other.x, self.y + other.y)
8
9 def __repr__(self):
10 return f"Vector({self.x}, {self.y})"
11
12 # Other arithmetic magic methods:
13 # def __sub__(self, other): # Subtraction (-)
14 # def __mul__(self, other): # Multiplication (*)
15 # def __truediv__(self, other): # True division (/)
16 # def __floordiv__(self, other): # Floor division (//)
17 # def __mod__(self, other): # Modulo (%)
18 # def __pow__(self, other): # Exponentiation (**)
19
20v1 = Vector(1, 2)
21v2 = Vector(3, 4)
22print(v1 + v2) # Vector(4, 6)
Altri metodi magici aritmetici includono i seguenti:.
Metodo | Operatore |
---|---|
__add__ |
+ |
__sub__ |
- |
__mul__ |
* |
__truediv__ |
/ |
__floordiv__ |
// |
__mod__ |
% |
__pow__ |
** |
Personalizzazione degli operatori di confronto
Puoi anche fare l’overloading degli operatori di confronto. Ad esempio, il metodo __eq__
permette di fare l’overloading dell’operatore di uguaglianza.
1class Box:
2 def __init__(self, volume):
3 self.volume = volume
4
5 def __eq__(self, other):
6 return self.volume == other.volume
7
8 def __lt__(self, other):
9 return self.volume < other.volume
10
11 # Comparison magic methods:
12 # def __eq__(self, other): # Equal to (==)
13 # def __ne__(self, other): # Not equal to (!=)
14 # def __lt__(self, other): # Less than (<)
15 # def __le__(self, other): # Less than or equal to (<=)
16 # def __gt__(self, other): # Greater than (>)
17 # def __ge__(self, other): # Greater than or equal to (>=)
18
19b1 = Box(100)
20b2 = Box(200)
21
22print(b1 == b2) # False
23print(b1 < b2) # True
Esistono anche i seguenti metodi magici:. Questi metodi magici definiscono confronti come l’uguaglianza e l’ordine tra oggetti.
Operatore | Metodo magico |
---|---|
== |
__eq__ |
!= |
__ne__ |
< |
__lt__ |
<= |
__le__ |
> |
__gt__ |
>= |
__ge__ |
Metodi magici per i tipi contenitori
Puoi creare classi che si comportano come liste o dizionari.
__len__
: Ottenere il numero di elementi
Il metodo __len__
è un metodo magico che restituisce il numero di elementi.
1class Basket:
2 def __init__(self, items):
3 self.items = items
4
5 def __len__(self):
6 return len(self.items)
7
8basket = Basket(["apple", "banana"])
9print(len(basket)) # 2
__getitem__
: Accesso tramite indice
Il metodo __getitem__
viene chiamato quando si utilizza l’accesso tramite indice.
1class Basket:
2 def __init__(self, items):
3 self.items = items
4
5 def __getitem__(self, index):
6 return self.items[index]
7
8basket = Basket(["apple", "banana"])
9print(basket[1]) # banana
__setitem__
e __delitem__
: Scrittura ed eliminazione
I metodi __setitem__
e __delitem__
vengono chiamati quando si scrivono o si eliminano elementi.
1class Basket:
2 def __init__(self, items):
3 self.items = items
4
5 def __setitem__(self, index, value):
6 self.items[index] = value
7
8 def __delitem__(self, index):
9 del self.items[index]
10
11basket = Basket(["apple", "banana"])
12basket[1] = "grape"
13del basket[0]
14print(basket.items) # ['grape']
Metodi magici per l’iterazione
Per rendere un oggetto iterabile in un ciclo for
, implementa quanto segue:.
__iter__
e __next__
1class Counter:
2 def __init__(self, limit):
3 self.limit = limit
4 self.current = 0
5
6 def __iter__(self):
7 return self
8
9 def __next__(self):
10 if self.current >= self.limit:
11 raise StopIteration
12 self.current += 1
13 return self.current
14
15for num in Counter(3):
16 print(num)
17# Output:
18# 1
19# 2
20# 3
Gestore di contesto (istruzione with
)
Definendo i metodi __enter__
e __exit__
, puoi implementare la logica di pre- e post-elaborazione per l’istruzione with
.
1class FileOpener:
2 def __init__(self, filename):
3 self.filename = filename
4
5 def __enter__(self):
6 self.file = open(self.filename, 'r')
7 return self.file
8
9 def __exit__(self, exc_type, exc_val, exc_tb):
10 self.file.close()
11
12with FileOpener("example.txt") as f:
13 content = f.read()
14 print(content)
Oggetti chiamabili: __call__
Definendo il metodo __call__
, è possibile rendere un’istanza chiamabile come una funzione.
1class Greeter:
2 def __init__(self, greeting):
3 self.greeting = greeting
4
5 def __call__(self, name):
6 return f"{self.greeting}, {name}!"
7
8hello = Greeter("Hello")
9print(hello("Alice")) # Hello, Alice!
Riepilogo
I metodi magici in Python sono un modo potente per aggiungere comportamenti naturali e intuitivi alle classi. Ogni metodo ha uno scopo preciso e implementandoli correttamente puoi scrivere codice più flessibile e Pythonic.
I metodi magici fungono da ‘interfaccia invisibile’ che supporta il modo in cui gli oggetti Python interagiscono e si comportano dietro le quinte.
Puoi seguire l'articolo sopra utilizzando Visual Studio Code sul nostro canale YouTube. Controlla anche il nostro canale YouTube.