2015-06-19 2 views
9

Ich muss in der Lage sein, ein Flag auf einer Klasse (nicht für eine Instanz einer Klasse) zu setzen, die für eine Unterklasse nicht sichtbar ist. Die Frage ist, ist es möglich, und wie würde ich es tun, wenn es ist?Wie fügt man dem Python * class * ein Attribut hinzu, das _nicht_ geerbt ist?

Zur Veranschaulichung, ich möchte etwas wie folgt aus:

class Master(SomeOtherClass): 
    __flag__ = True 

class Child(Master): 
    pass 

... wo hasattr(Master, "__flag__")True für Master aber False für Child zurückkehren. Ist das möglich? Wenn das so ist, wie? Ich möchte in keinem Kind explizit auf false setzen müssen.

Mein erster Gedanke war, __metaclass__ zu definieren, aber ich habe nicht den Luxus, das zu tun, weil Master von einigen anderen Klassen und Metaklassen erbt, die ich nicht kontrolliere und die privat sind.

Letztlich also bin ich wollen ein Dekorateur schreiben, dass ich so etwas tun kann:

@hide_this 
class Master(SomeOtherClass): pass 

@hide_this 
class Child(Master): pass 

class GrandChild(Child): pass 
... 
for cls in (Master, Child, GrandChild) 
    if cls.__hidden__: 
     # Master, Child 
    else: 
     # GrandChild 
+1

Sie könnten es "__hidden" machen, dann würden nur Klassen, in denen es direkt definiert wurde, ein '_ClassName__hidden' Attribut haben. – jonrsharpe

+0

Gibt es einen Grund, warum du nicht "cls .__ dict __. Get ('__ hidden __')" schreiben willst, außer dass es hässlich ist? –

+0

@jonrsharpe: Nein, diese Lösung ist mir nicht eingefallen. Das wird fantastisch funktionieren. Schreibe eine Antwort auf, damit ich sie annehmen kann, wenn du willst. Wenn Sie dies nicht tun, füge ich die Antwort selbst zur späteren Bezugnahme hinzu. Vielen Dank! –

Antwort

4

Sie ganz in der Nähe waren:

class Master(SomeOtherClass): 
    __flag = True 

class Child(Master): 
    pass 

Zwei führende unterstreicht ohne Hinterruft unterstreicht Name Mangling, so wird das Attribut _Master__flag benannt. Deshalb, wenn Sie überprüfen:

hasattr(cls, '_{}__flag'.format(cls.__name__)) 

wird es nur True für Master, nicht Child.

+0

Das ist nicht genau was ich suche - ich habe keine Instanz der Klasse, ich habe nur die Klasse. Die Technik funktioniert jedoch genauso. –

+0

@BryanOakley Ja, es ist das gleiche mit Klassen; entsprechend aktualisiert! – jonrsharpe

+0

Ausgezeichnet. Vielen Dank. Ich habe es bereits in meinem Code implementiert. –

Verwandte Themen