Die __new__
-Methode verstehen und verwenden
In diesem Schritt werden wir die __new__()
-Methode in Python-Klassen untersuchen. Während __init__()
üblicherweise zur Initialisierung von Objektattributen nach der Erstellung verwendet wird, ist __new__()
die Methode, die bevor die Instanz erstellt wird, aufgerufen wird. Sie ist für die Erstellung und Rückgabe des neuen Instanzobjekts verantwortlich.
Die Hauptunterschiede zwischen __new__()
und __init__()
sind:
__init__()
wird nachdem die Instanz erstellt wurde, aufgerufen. Ihr erstes Argument ist self
, das sich auf die Instanz selbst bezieht. Sie muss nichts zurückgeben.
__new__()
wird bevor die Instanz erstellt wird, aufgerufen. Ihr erstes Argument ist cls
, das sich auf die Klasse selbst bezieht. Sie muss das neue Instanzobjekt zurückgeben.
Meistens müssen Sie __new__()
nicht definieren, da die Standardimplementierung, die von der object
-Klasse geerbt wird, die Instanzerstellung übernimmt. Wenn Sie jedoch den Instanzerstellungsprozess anpassen müssen (z. B. zur Implementierung von Singletons oder unveränderlichen Objekten), können Sie __new__()
überschreiben.
Beim Überschreiben von __new__()
rufen Sie typischerweise die __new__()
-Methode der Elternklasse mit super().__new__(cls)
auf und geben das Ergebnis zurück. Alle an den Klassenkonstruktor übergebenen Argumente (außer cls
) werden dann an die __init__()
-Methode weitergegeben.
Erstellen wir ein einfaches Beispiel, um __new__()
in Aktion zu sehen. Wir erstellen eine Klasse Dog
, die von Animal
erbt, und fügen eine __new__()
-Methode hinzu, um eine Nachricht auszugeben, wenn eine neue Dog
-Instanz erstellt wird.
Öffnen Sie die Datei dog_cat.py
im VS Code-Editor. Wenn die Datei nicht existiert, erstellen Sie sie im Verzeichnis ~/project
.
code ~/project/dog_cat.py
Fügen Sie den folgenden Code zur Datei dog_cat.py
hinzu:
## File Name: dog_cat.py
class Animal:
def __init__(self, name):
self._name = name
def get_name(self):
return self._name
def set_name(self, value):
self._name = value
def say(self):
print(self._name + ' is saying something')
class Dog(Animal):
## Note that the first parameter of this method is cls, which points to the class itself
## The parameters used in the __init__ method must be included, except for self
def __new__(cls, name, age):
print('A new dog is being created.')
## Use the super method to call the parent class's method with the same name
return super().__new__(cls)
## The line below has the same effect as the line above, both return the result of calling the parent class method
#return object.__new__(cls)
def __init__(self, name, age):
super().__init__(name)
self.age = age
def say(self):
print(self._name + ' is making sound wang wang wang...')
Speichern Sie die Datei.
Öffnen Sie nun ein neues Terminal in VS Code und führen Sie dieses Skript mit dem Befehl python
aus, um die Ausgabe der __new__
-Methode zu sehen.
python ~/project/dog_cat.py
Sie werden noch keine Ausgabe sehen, da wir noch keine Instanz der Dog
-Klasse erstellt haben. Fügen wir Code hinzu, um eine Dog
-Instanz zu erstellen und sie auszugeben.
Ändern Sie die Datei dog_cat.py
und fügen Sie am Ende die folgenden Zeilen hinzu:
## File Name: dog_cat.py
class Animal:
def __init__(self, name):
self._name = name
def get_name(self):
return self._name
def set_name(self, value):
self._name = value
def say(self):
print(self._name + ' is saying something')
class Dog(Animal):
## Note that the first parameter of this method is cls, which points to the class itself
## The parameters used in the __init__ method must be included, except for self
def __new__(cls, name, age):
print('A new dog is being created.')
## Use the super method to call the parent class's method with the same name
return super().__new__(cls)
## The line below has the same effect as the line above, both return the result of calling the parent class method
#return object.__new__(cls)
def __init__(self, name, age):
super().__init__(name)
self.age = age
def say(self):
print(self._name + ' is making sound wang wang wang...')
## Create a Dog instance
d = Dog('Tom', 11)
print(d)
Speichern Sie die Datei und führen Sie sie erneut im Terminal aus:
python ~/project/dog_cat.py
Sie sollten die Ausgabe der __new__
-Methode sehen, bevor die Instanz ausgegeben wird.
A new dog is being created.
<__main__.Dog object at 0x...>
Dies zeigt, dass die __new__
-Methode vor der __init__
-Methode aufgerufen wird und für die Erstellung des Instanzobjekts verantwortlich ist.