Chromium Code Reviews| OLD | NEW |
|---|---|
| (Empty) | |
| 1 # Copyright 2014 The Chromium Authors. All rights reserved. | |
| 2 # Use of this source code is governed by a BSD-style license that can be | |
| 3 # found in the LICENSE file. | |
| 4 | |
| 5 class cached_property(object): | |
|
Vadim Sh.
2014/06/27 18:26:22
Mention somewhere that it's not thread safe.
iannucci
2014/06/28 08:33:35
Done.
| |
| 6 """Like @property, except that the result of get is cached on | |
| 7 self.{'_' + fn.__name__}. | |
| 8 | |
| 9 >>> class Test(object): | |
| 10 ... @cached_property | |
| 11 ... def foo(self): | |
| 12 ... print "hello" | |
| 13 ... return 10 | |
| 14 ... | |
| 15 >>> t = Test() | |
| 16 >>> t.foo | |
| 17 hello | |
| 18 10 | |
| 19 >>> t.foo | |
| 20 10 | |
| 21 >>> t.foo = 20 | |
| 22 >>> t.foo | |
| 23 20 | |
| 24 >>> del t.foo | |
| 25 >>> t.foo | |
| 26 hello | |
| 27 10 | |
| 28 >>> | |
| 29 """ | |
| 30 def __init__(self, fn): | |
| 31 self.func = fn | |
| 32 self._iname = "_" + fn.__name__ | |
| 33 self.__name__ = fn.__name__ | |
|
Vadim Sh.
2014/06/27 18:26:22
Use functools.update_wrapper, it's exactly what it
iannucci
2014/06/28 08:33:35
Done.
| |
| 34 self.__doc__ = fn.__doc__ | |
| 35 self.__module__ = fn.__module__ | |
| 36 | |
| 37 def __get__(self, inst, cls=None): | |
| 38 if inst is None: | |
| 39 return self | |
| 40 if not hasattr(inst, self._iname): | |
| 41 val = self.func(inst) | |
| 42 # Some methods call out to another layer to calculate the value. This | |
| 43 # higher layer will assign directly to the property, so we have to do | |
| 44 # the extra hasattr here to determine if the value has been set as a side | |
| 45 # effect of func() | |
| 46 if not hasattr(inst, self._iname): | |
| 47 setattr(inst, self._iname, val) | |
| 48 return getattr(inst, self._iname) | |
| 49 | |
| 50 def __delete__(self, inst): | |
| 51 assert inst is not None | |
| 52 if hasattr(inst, self._iname): | |
| 53 delattr(inst, self._iname) | |
| OLD | NEW |