Le premier problème est que le décorateur est exécuté lors de la création de la classe, et pas de l'instance, donc il n'est pas possible d'accéder à self dans le décorateur.
Ma première tentative a donc été:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
| class Spam :
def __init__(self,verbose):
self.verbose = verbose
self.name = 'Spam'
@staticmethod
def deco(func):
def sub (self, *k, **a):
if self.verbose: # NB j'accède au self de l'instance
print 'entering', self.name
return func(self, *k, **a) # execute la methode
return sub
@Spam.deco
def eggs(self,x):
return x+1
s = Spam(True)
x = s.eggs(5) |
Mais cela ne fonctionne pas:
TypeError: unbound method deco() must be called with Spam instance as first argument (got function instance instead)
Bizarre que Spam.deco soit vue comme une unbound method alors que c'est censé être une méthode statique... C'est sans doute lié à la façon donc la classe est construite.
Par contre ceci, qui semble un peu étrange, fonctionne:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| class Spam :
def __init__(self,verbose):
self.verbose = verbose
self.name = 'Spam'
def deco(func):
def sub (self, *k, **a):
if self.verbose: # NB j'accède au self de l'instance
print 'entering', self.name
return func(self, *k, **a) # execute la methode
return sub
@deco
def eggs(self,x):
return x+1
s = Spam(True)
x = s.eggs(5) |
Dans ce cas, je pense que '@deco' appelle en réalité la fonction deco, qui sera promue en méthode d'instance au sein de la classe.
Mais en réalité, ce n'a plus aucun intérêt de faire du décorateur une méthode, autant en faire une gentille fonction en dehors de la classe.
[EDIT]
Ceci fonctionne aussi et est peut-être un peu plus propre, mais toujours aussi inutile:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| class Spam :
def __init__(self,verbose):
self.verbose = verbose
self.name = 'Spam'
def deco(func):
def sub (self, *k, **a):
if self.verbose: # NB j'accède au self de l'instance
print 'entering', self.name
return func(self, *k, **a) # execute la methode
return sub
@deco
def eggs(self,x):
return x+1
deco = staticmethod(deco)
s = Spam(True)
x = s.eggs(5) |
Partager