C'est jamais évident de trouver le bon angle.
Peut-être en comparant avec un truc connu : on est bien d'accord que toutes les classes possèdent un dictionnaire (__dict__
) qui référence ses méthodes ? (str.__dict__
référence toutes les méthodes de la classe str
).
Bien, donc ça veut dire qu'à un moment donné, on passe de ceci :
| class Foo:
def une_methode(self):
pass
def une_autre_methode(self):
pass
|
À cela :
| >>> Foo.__dict__
mappingproxy({'une_autre_methode': <function Foo.une_autre_methode at 0x7f929bde97b8> ...
|
Pour que Foo
ait un attribut, il faut qu'à un moment on ait appelé un constructeur qui l'a initialisé et rempli ce dictionnaire.
OK ?
He bien ce constructeur, c'est le constructeur de la classe type
:
| >>> isinstance(Foo, type)
True
|
C'est le constructeur qui "construit les classes" quand Python a fini de les parser.
Par chance, en Python, (et c'est là le truc qui donne le vertige) type
est… une classe. Vu qu'on aime pas trop raisonner avec des miroirs qui se réfléchissent à l'infini, on dira que type
est une méta-classe, parce que quand on instancie type
, on obtient une classe.
Donc si on remet tout bout à bout : dans le tuto j'ai besoin qu'un attribut soit initialisé un peu comme l'attribut __dict__
des classes, c'est-à-dire automatiquement chaque fois que je déclare un Dispatcher. Comme c'est dans le constructeur de type
que ça se passe, eh bien je crée une classe qui hérite de type
et je surcharge son constructeur pour y ajouter ma tambouille.
C'est peut-être plus clair comme ça ?