Would either of the existing solutions work for you? class X: def __init__(self, name): self.name = name @cached_property def title(self): print("compute title once") return self.name.title() @property @lru_cache def upper(self): print("compute uppper once") return self.name.upper()
The second one seems a bit dangerous in that it will erroneously
keep objects alive until they are either ejected from the cache or
until the class itself is collected (plus only 128 objects would
be in the cache at one time): https://bugs.python.org/issue19859
I am -0 on adding `call_once = lru_cache(maxsize=None)` here. I feel like it could be misleading in that people might think that it ensures that the function is called exactly once (it reminds me of the FnOnce trait in Rust), and all it buys us is a nice way to advertise "here's a use case for lru_cache".Thanks for the concrete example. AFAICT, it doesn't require (and probably shouldn't have) a lock to be held for the duration of the call. Would it be fair to say the 100% of your needs would be met if we just added this to the functools module? call_once = lru_cache(maxsize=None)