Chcę zastąpić moje metody klasy Python __getattribute__
i __setattr__
. Mój przypadek użycia jest zwykle jeden: Mam kilka specjalnych nazw, które chcę obsługiwać, i chcę domyślne zachowanie dla czegokolwiek innego. W przypadku __getattribute__
wydaje się, że mogę zażądać domyślnego zachowania po prostu podnosząc AttributeError
. Jak jednak osiągnąć to samo w __setattr__
? Oto banalny przykład, implementujący klasę z niezmiennymi polami "A", "B" i "C".Jak poprawnie zastąpić __setattr__ i __getattribute__ dla klas w nowym stylu w Pythonie?
class ABCImmutable(SomeSuperclass):
def __getattribute__(self, name):
if name in ("A", "B", "C"):
return "Immutable value of %s" % name
else:
# This should trigger the default behavior for any other
# attribute name.
raise AttributeError()
def __setattr__(self, name, value):
if name in ("A", "B", "C"):
raise AttributeError("%s is an immutable attribute.")
else:
# How do I request the default behavior?
???
Co jest na miejscu ze znakami zapytania? W przypadku klas w starym stylu odpowiedź brzmiała: self.__dict__[name] = value
, ale dokumentacja wskazuje, że jest to niewłaściwe w przypadku klas w nowym stylu.
"dokumentacja wskazuje, że jest to niewłaściwe w przypadku zajęć w nowym stylu" ... i czy nie wskazano, co jest właściwe w przypadku zajęć w nowym stylu? – Gerrat
Dlaczego po prostu nie implementujesz nazwanych pól jako właściwości tylko do ustawienia? – katrielalex
Niezmienność była po prostu trywialnym przykładem użycia __setattr__. Moje faktyczne użycie jest nieco bardziej skomplikowane. Moja klasa dziedziczy po Dict, ale dodatkowo niektóre specjalne klucze (określone w czasie wykonywania) są dostępne jako "object.key" zamiast "object ['key']". Prawdopodobnie mógłbym dodać je jako właściwości za pomocą środowiska wykonawczego lub coś podobnego, ale łatwiej używać "__getattr__" i "__setattr__", a wydajność nie jest szczególnie krytyczna. –