python - Elegant way to add functionality to previously defined functions -


how combine 2 functions together

i have class controlling hardware:

class heater()     def set_power(self,dutycycle, period)        ...     def turn_on(self)        ...     def turn_off(self) 

and class connects database , handles data logging functionality experiment:

class datalogger()     def __init__(self)         # record measurements , controls in database     def start(self,t)         # starts new thread acquire , record measuements every t seconds 

now, in program recipe.py want like:

        log = datalogger()          @datalogger_decorator         h1 = heater()          log.start(60)          h1.set_power(10,100)         h1.turn_on()         sleep(10)         h1.turn_off()         etc 

where actions on h1 recorded datalogger. can change of classes involved, looking elegant way this. ideally hardware functions remain separated database , datalogger functions. , ideally datalogger reusable other controls , measurements.

for scenario, prefer using datalogger baseclass or mixin other classes rather trying sort of decorator magic (which doesn't click me pythonic way use decorator)

e.g.:

class datalogger(object):   def __init__(self):       # init stuff    def startlog(self, t):       # start log    class heater(datalogger):    def __init__(self):       # stuff before initing datalogger       super(heater, self).__init__() # init datalogger    #other functions 

that way can do:

h1 = heater() h1.startlog(5) h1.do_other_stuff() 

an example uses mixin existing class:

class dataloggermixin(object):    def __init__(self):     # init things     super(datalogger, this).__init__()  # trigger next __init__ call in inheritance chain (i.e. whatever mix with)  class heater(object):     """ here's heater have lying around doesn't data logging.  no need change it."""  # add new child class 2 lines, includes dataloggermixin first parent class, , have new class datalogging functionality , heater functionality.  class loggingheater(dataloggermixin, heater):     """ data logging heater """     pass  # no further code should necessary if list dataloggermixin first in base classes.    >>> logging_heater = loggingheater() >>> logging_heater.start_log(5) >>> logging_heater.do_heater_stuff() 

the key using mixins in python understand how method resolution order (mro), particularly super, works in multiple inheritance situation. see this on cooperative multiple inheritance.

____________________________________________________________________ 

alternative method: use wrapper class

if mixin methodology doesn't work scheme, option use datalogger wrapper class objects logged. data logger accept object logging on in constructor so:

class datalogger(object)   def __init__(self, object_to_log)     self.object = object_to_log   # have access self.object in methods.     # record measurements , controls in database   def start(self,t)     # starts new thread aqcuire , reccord measuements every t secconds 

i'm not sure type of logging or monitoring done , whether need access object you're logging or if independent. if former, presumably heater, valve, etc. implement same functions datalogger cares can log them regardless of class are. (this handy core feature of dynamic languages python called "duck typing", can operate on different types, long types implement functions or attributes care about. "if quacks duck . . .")

your code might more this, using wrapper class methodology:

h1 = heater()  log = datalogger(h1) log.start(60) h1.set_power(10,100) h1.turn_on() sleep(10) h1.turn_off() 

hope helps!


Comments

Popular posts from this blog

django - How can I change user group without delete record -

java - Need to add SOAP security token -

java - EclipseLink JPA Object is not a known entity type -