Python сбрасываемый декоратор памятки (для определенного случая) - PullRequest
0 голосов
/ 23 декабря 2011

Этот вопрос является продолжением ответа для Python сбрасываемого экземпляра метода напоминания декоратора . На самом деле, я бы написал это как комментарий к этому ответу, но у меня (пока, я надеюсь) недостаточно репутации.

В этом ответе @aix дает хороший подход к сбросу запомненных функций с помощью декораторов.

«Проблема» с этим ответом состоит в том, что вызов reset для определенного декорированного метода сбрасывает кэш для всех экземпляров. Пример, использующий те же классы, определенные @aix, должен прояснить:

c = my_class()
print c.my_func(55)
# This time the function is computed and stored in cache
print c.my_func(55)
# This second call is cached...  no computation needed
d = my_class()
d.my_func.reset()
print c.my_func(55)
# This third call is also computed, since the cache has been cleared

Я думаю, что d.my_func.reset() должен очищать кэш только для предварительно вычисленных значений d.my_func, а не для всех других экземпляров my_class.

У меня есть полу-решение, которое не убеждает полностью, но я думаю, что кто-то может улучшить.

Я изменил метод reset() и ввел параметр instance:

  def _reset(self,instance):
  for cached in self.cache.keys():
      if cached[0] == instance:
          del self.cache[cached] 

Теперь, если я сделаю:

c = my_class()
print c.my_func(55)
# This time the function is computed and stored in cache
print c.my_func(55)
# This second call is cached
d = my_class()
d.my_func.reset(d)
print c.my_func(55)
# Now this third call is cached

Однако способ вызова метода сброса: d.my_func.reset(d) кажется (по крайней мере) уродливым, но я не смог найти лучшего решения ... У кого-нибудь есть идеи?

Спасибо!

Редактировать

Для записи: вместо передачи экземпляра в качестве параметра, вы можете получить то же поведение, изменяя метод декоратора __get__.

Добавьте self.original_self = obj в методе __get__(self, obj, objtype) и замените if cached[0] == instance на if cached[0] == self.original_self в методе _reset. Это решает проблему!

1 Ответ

0 голосов
/ 23 декабря 2011

Вы можете использовать атрибут __self__ метода (в данном случае self.__self__), чтобы найти экземпляр класса, к которому он привязан (вместо того, чтобы также передавать экземпляр).

...