Vous pouvez le faire en utilisant un __getattr__
hook sur un metaclass.
class DefaultClassMethods(type):
def __getattr__(cls, attr):
def _defaultClassMethod(cls):
print 'Hi, I am the default class method!'
setattr(cls, attr, classmethod(_defaultClassMethod))
return getattr(cls, attr)
Démo:
>>> class DefaultClassMethods(type):
... def __getattr__(cls, attr):
... def _defaultClassMethod(cls):
... print 'Hi, I am the default class method!'
... setattr(cls, attr, classmethod(_defaultClassMethod))
... return getattr(cls, attr)
...
>>> class A(object):
... __metaclass__ = DefaultClassMethods
...
>>> A.spam
<bound method DefaultClassMethods._defaultClassMethod of <class '__main__.A'>>
>>> A.spam()
Hi, I am the default class method!
Notez que nous avons mis le résultat de la ligne droite appel classmethod
sur la classe, il cache efficacement pour les recherches futures.
Si vous avez besoin de régénérer la méthode de classe à chaque appel à la place, utiliser le même method to bind a function to an instance mais avec la classe à la place et métaclasse (en utilisant cls.__metaclass__
être compatible avec métaclasse subclassing):
from types import MethodType
class DefaultClassMethods(type):
def __getattr__(cls, attr):
def _defaultClassMethod(cls):
print 'Hi, I am the default class method!'
return _defaultClassMethod.__get__(cls, cls.__metaclass__)
Pour les méthodes statiques juste retourner la fonction directement dans tous les cas, pas besoin de muck avec le décorateur staticmethod
ou le protocole descripteur.
A.asd() - AttributeError: « objet de type 'A' a pas d'attribut 'asd' " –
@EcirHana: ah, vous voulez dire une méthode de classe par défaut, va mettre à jour. –
Je souhaite que le spam soit une méthode de classe, pas une méthode d'instance. –