Die vollständige Komplexität der OOP-Implementierung von Python geht weit über den Umfang einer Stack Overflow-Antwort hinaus, aber es ist möglich, einen Überblick zu geben. Dies wird viele Details wie Metaklassen, Mehrfachvererbung, Deskriptoren und die C-Level-API beschönigen. Dennoch sollte es Ihnen ein Gefühl dafür geben, warum so etwas möglich ist, sowie einen allgemeinen Eindruck davon, wie es gemacht wird. Wenn Sie die vollständigen Details wünschen, sollten Sie die CPython source code durchsuchen.
Ein Objekt wie eine Instanz Ihrer Person
Klasse besteht aus folgenden Dinge:
- Eine Klasse
- A dict seine Attribute
- Andere Sachen halten, die im Moment nicht relevant ist, wie
__weakref__
.
Eine Klasse ist auch ziemlich einfach. Es hat
- Basisklasse
- A dict seine Attribute
- Andere Sachen halten, die im Moment nicht relevant ist, wie der Klassenname.
Wenn Sie eine Klasse mit einer class
Anweisung definieren, bündelt Python einen Zeiger auf die Basisklasse bis sie (oder object
wenn Sie nicht ein Pick DID) gepickt und ein dict die Methoden halten Sie definiert sind, und das ist dein neues Klassenobjekt. Es ist ein bisschen wie das folgende Tupel
Person = (object,
{'__init__': <that __init__ method you wrote>,
'getInfo': <that getInfo method you wrote>},
those irrelevant bits we're glossing over)
aber kein Tupel. (Bei C-Ebene ist diese Platte fast, aber nicht ganz, als eine Struktur implementiert.)
Wenn Sie eine Instanz der Klasse zu erstellen, bündelt Python einen Zeiger auf die Klasse zusammen und eine neue dict für die Instanzattribute, und das ist Ihre Instanz.Es ist ein bisschen wie das folgende Tupel:
personOne = (Person, {}, those irrelevant bits we're glossing over)
aber wieder, kein Tupel. Wiederum ist es fast, aber nicht ganz, als eine Struktur auf C-Ebene implementiert.
Dann läuft es __init__
, vorbei __init__
die neue Instanz und was auch immer andere Argumente, die Sie zu Ihrer Klasse zur Verfügung gestellt:
Person.__init__(personOne, "Bob", 34)
Attribut Zuordnung zu setzende Einträgen in dem dict Objekt übersetzt wird, so die Zuordnungen in __init__
:
def __init__(self, name, age):
self.name = name
self.age = age
Ursache der dict in folgendem Zustand am Ende:
{'name': 'Bob', 'age': 34}
Wenn Sie personOne.getInfo()
nennen, sucht Python in personOne
‚s dict, dann dict seiner Klasse, dann dict seine Superklasse usw., bis es einen Eintrag für den 'getInfo'
Schlüssel findet. Der zugehörige Wert ist die getInfo
Methode. Wenn die Methode in einem Klassendikt gefunden wurde, fügt Python personOne
als erstes Argument ein. (Die Einzelheiten, wie dieses Argument eingefügt werden kann, sind in der descriptor protocol.)