4 Stimmen

Python - Überschreiben __getattribute__ für eine Instanz?

Das scheint mir ein bisschen schwierig zu sein. Vor einiger Zeit habe ich es bereits geschafft, die Methode einer Instanz mit etwas wie zu überschreiben:

def my_method(self, attr):
    pass

instancemethod = type(self.method_to_overwrite)
self.method_to_overwrite = instancemethod(my_method, self, self.__class__)

was bei mir sehr gut funktioniert hat; aber jetzt versuche ich, die Instanz zu überschreiben __getattribute__() Funktion, die bei mir aus dem Grund nicht funktioniert, weil die Methode anscheinend

<type 'method-wrapper'>

Ist es möglich, etwas dagegen zu tun? Ich konnte keine anständige Python-Dokumentation finden über method-wrapper .

6voto

Ants Aasma Punkte 50286

Sie möchten den Algorithmus für die Attributsuche pro Instanz außer Kraft setzen? Ohne zu wissen, warum Sie das tun wollen, würde ich die Vermutung wagen, dass es einen saubereren, weniger komplizierten Weg gibt, das zu tun, was Sie tun müssen. Wenn Sie das wirklich müssen, dann müssen Sie, wie Aaron sagte, eine Umleitung installieren __getattribute__ Handler für die Klasse, da Python spezielle Methoden nur in der Klasse nachschlägt und alles, was in der Instanz definiert ist, ignoriert.

Sie müssen auch besonders vorsichtig sein, um nicht in eine unendliche Rekursion zu geraten:

class FunkyAttributeLookup(object):
    def __getattribute__(self, key):
        try:
            # Lookup the per instance function via objects attribute lookup
            # to avoid infinite recursion.
            getter = object.__getattribute__(self, 'instance_getattribute')
            return getter(key)
        except AttributeError:
            return object.__getattribute__(self, key)

f = FunkyAttributeLookup()
f.instance_getattribute = lambda attr: attr.upper()
print(f.foo) # FOO

Auch, wenn Sie Methoden auf Ihre Instanz überschreiben, müssen Sie nicht die Methode Objekt selbst instanziieren, können Sie entweder das Deskriptor-Protokoll auf Funktionen, die die Methoden erzeugt oder nur Curry das Argument self.

 #descriptor protocol
 self.method_to_overwrite = my_method.__get__(self, type(self))
 # or curry
 from functools import partial
 self.method_to_overwrite = partial(my_method, self)

1 Stimmen

Ich wusste nicht, dass "Python spezielle Methoden nur in der Klasse nachschlägt und alles ignoriert, was in der Instanz definiert ist.". Vielen Dank dafür! Ich habe keine Fehlermeldung erhalten, aber es schien, als würde Python mich ignorieren Es sollte eine Art von Ausnahmen ausgelöst werden? Ich weiß nicht

4voto

2voto

Aaron Digulla Punkte 308693

Es gibt eine Reihe von Methoden, die Sie nicht überschreiben können und __getattribute__() ist einer von ihnen.

2 Stimmen

__getattribute__() IS genannt wird, auch wenn es ein Attribut mit diesem Namen gibt. Was Sie sagten, ist wahr für __getattr__() Methode.

1 Stimmen

-1 an Python für die Verwirrung, die durch __getattr__ , __getattribute__ y __setattr__

0 Stimmen

Sie haben Recht; ich habe meine fehlerhafte Implementierung entfernt. Die Lösung von Ants ist korrekt.

1voto

jldupont Punkte 87330

Ich glaube methoden-rapper ist ein Wrapper um eine in C geschriebene Methode.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X