Reputation: 33
I would like to store a number of temperature values as a dictionary instance attribute. Whenever the dictionary key is used, I would like the corresponding value to update, with behaviour similar to that of an instance @property
decorator.
Is there a way to to this without updating the entire dictionary? Below is code of how I'd expect it to pan out, with simplified update functions (the real ones will read from sensors), but the temperatures need to update on each access.
import random
class Thermal():
def __init__(self):
self.temperatures = {'outside': self.outside, 'inside': self.inside}
@property
def outside(self):
return random.random()
@property
def inside(self):
return 1 + random.random()
@property
def c(self):
return random.random()
a = Thermal()
print(a.temperatures['outside'])
print(a.temperatures['outside'])
print(a.temperatures['inside'])
print(a.temperatures['inside'])
The outside
and inside
temperatures printed above do not change on access, though of course it works for the basic attribute, c
. Is this a case where I need to create a dict subclass, or is there another way to do it?
I can resign to having individual instance attributes for each temperature, but I think it's neater in a dictionary and am keen to see if there is a way to achieve this.
Upvotes: 1
Views: 79
Reputation: 8550
With minimal changes to your code and keeping the semantics like a.temperatures['outside']
here is possible solution:
import random
class Temperatures(): # here
def __init__(self, thermal):
self.thermal = thermal
def __getitem__(self, item):
return getattr(self.thermal, item)
class Thermal():
def __init__(self):
self.temperatures = Temperatures(self) # and here
@property
def outside(self):
return random.random()
@property
def inside(self):
return 1 + random.random()
@property
def c(self):
return random.random()
a = Thermal()
print(a.temperatures['outside'])
print(a.temperatures['outside']) # will give different random number
print(a.temperatures['inside'])
print(a.temperatures['inside'])
Upvotes: 2
Reputation: 19905
How about this?
class Thermal:
def __init__(self):
self._temperatures = {'inside': None, 'outside': None}
def __getitem__(self, key):
self.update()
return self._temperatures[key]
def update(self):
# update temperatures here...
Upvotes: 1