diff options
| author | Joshua Harlow <harlowja@gmail.com> | 2016-02-08 23:16:58 -0800 |
|---|---|---|
| committer | Joshua Harlow <harlowja@gmail.com> | 2016-02-08 23:16:58 -0800 |
| commit | b033fa672227720ae64bca25eafffc87d5fea42a (patch) | |
| tree | 827ac619760ba6c55683ffcdebf79c94397ebfda /taskflow/utils | |
| parent | 61efc31e965b8defac84aa494095fd3734f739eb (diff) | |
| download | taskflow-b033fa672227720ae64bca25eafffc87d5fea42a.tar.gz | |
Allow cachedproperty to avoid locking
Under some cirumstances it is ok to recompute
a value when raced to by multiple threads, for these
cases allow the cachedproperty to avoid needing and
using a lock.
Change-Id: Icb71cb5ea280185cfb120671be900435dabcd50b
Diffstat (limited to 'taskflow/utils')
| -rw-r--r-- | taskflow/utils/misc.py | 33 |
1 files changed, 21 insertions, 12 deletions
diff --git a/taskflow/utils/misc.py b/taskflow/utils/misc.py index 5c2bf4f..3798a45 100644 --- a/taskflow/utils/misc.py +++ b/taskflow/utils/misc.py @@ -350,8 +350,11 @@ class cachedproperty(object): cached property would be stored under '_get_thing' in the self object after the first call to 'get_thing' occurs. """ - def __init__(self, fget): - self._lock = threading.RLock() + def __init__(self, fget=None, require_lock=True): + if require_lock: + self._lock = threading.RLock() + else: + self._lock = None # If a name is provided (as an argument) then this will be the string # to place the cached attribute under if not then it will be the # function itself to be wrapped into a property. @@ -365,10 +368,12 @@ class cachedproperty(object): self.__doc__ = None def __call__(self, fget): - # If __init__ received a string then this will be the function to be - # wrapped as a property (if __init__ got a function then this will not - # be called). + # If __init__ received a string or a lock boolean then this will be + # the function to be wrapped as a property (if __init__ got a + # function then this will not be called). self._fget = fget + if not self._attr_name: + self._attr_name = "_%s" % (fget.__name__) self.__doc__ = getattr(fget, '__doc__', None) return self @@ -387,13 +392,17 @@ class cachedproperty(object): if hasattr(instance, self._attr_name): return getattr(instance, self._attr_name) else: - with self._lock: - try: - return getattr(instance, self._attr_name) - except AttributeError: - value = self._fget(instance) - setattr(instance, self._attr_name, value) - return value + if self._lock is not None: + self._lock.acquire() + try: + return getattr(instance, self._attr_name) + except AttributeError: + value = self._fget(instance) + setattr(instance, self._attr_name, value) + return value + finally: + if self._lock is not None: + self._lock.release() def millis_to_datetime(milliseconds): |
