Re: generate methods at runtime, but the wrong one gets called
Maric Michaud a écrit : (snip) i don't get your design, it seems over-complicated to mee at first glance. aol / -- http://mail.python.org/mailman/listinfo/python-list
generate methods at runtime, but the wrong one gets called
Hello, I am writing an application that controls robots. Different robots can do different kinds of movements, such as e.g. open gripper, rotate gripper, etc. My RobotControl class should support all kinds of robots. I therefore delegate the actual control work to extra control-specific classes, one class per movement type, e.g. OpenGripperControl, RotateGripperControl. These movement control classes are created by a simple class factory. This is my class half-way through: class RobotControl: def __init__(self, movementTypes): self.__controls = {} motionControlFactory = MotionControlFactory() for movementType in movementTypes: self.__controls[movementType] = motionControlFactory.create(movementType) def __setMovementTypeValue(self, movementType, value): control = self.__controls[movementType] control.SetValue(value) # I want to provide methods like these to the client app, # but without typing them explicitely: def SetOpenGripper(self, value): self.__setMovementTypeValue('OpenGripper', value) def SetRotateGripper(self, value): self.__setMovementTypeValue('RotateGripper', value) My application: movementTypes = ['OpenGripper', 'RotateGripper'] robotCtrl = RobotControl(movementTypes) robotCtrl.SetOpenGripper(1.0) robotCtrl.SetRotateGripper(2.0) While control object creation is abstracted out into the class factory, SetOpenGripper(...) and SetRotateGripper(...) are still in there and I obviously want to get rid of them, at least in their explicitely implemented form. Instead, I want to generate them at runtime, depending on what movement types are required. I tried this in class RobotControl in __init__() in the 'for movementType ...' loop: funcName = 'Set' + movementType function = lambda self, value: self.__setMovementTypeValue(movementType, value) method = new.instancemethod(function, self, self.__class__) setattr(self, funcName, method) and the code somewhat seems to work, but instead of SetOpenGripper, SetRotateGripper is called. My questions: 1.) Does this look like a somewhat reasonable approach to someone who knows more about Python than me ? 2.) What could I be doing wrong ? I have a suspicion that my error is not even related to all this fancy runtime code generation stuff, but something really dumb and I've just been coding for too long to see it. http://mail.python.org/pipermail/python-list/2007-June/446601.html shows a somewhat comparable constellation and it was a good guideline. But there, the function is created by the class factory, as well and I unfortunately can't do that. Thank you very much, Steve -- http://mail.python.org/mailman/listinfo/python-list
Re: generate methods at runtime, but the wrong one gets called
Le Monday 25 August 2008 11:37:23 Steven Samuel Cole, vous avez écrit : Hello, I am writing an application that controls robots. Different robots can do different kinds of movements, such as e.g. open gripper, rotate gripper, etc. My RobotControl class should support all kinds of robots. I therefore delegate the actual control work to extra control-specific classes, one class per movement type, e.g. OpenGripperControl, RotateGripperControl. These movement control classes are created by a simple class factory. i don't get your design, it seems over-complicated to mee at first glance. This is my class half-way through: ... I tried this in class RobotControl in __init__() in the 'for movementType ...' loop: funcName = 'Set' + movementType function = lambda self, value: self.__setMovementTypeValue(movementType, value) method = new.instancemethod(function, self, self.__class__) setattr(self, funcName, method) and the code somewhat seems to work, but instead of SetOpenGripper, SetRotateGripper is called. The free variable movementType in the lambda is evaluated lately as it were in its last state once you return from __init__, if you want to early bind it to its value in each step of a for loop, you must use : func = lambda s, v, m_t=movementType : s.__setMovementTypeValue(m_t, v) My questions: 1.) Does this look like a somewhat reasonable approach to someone who knows more about Python than me ? At first, what you do is creating instancemethod and bound them to an instance of your class, I find this confusing. Why not just use __getattr__ special method ? (you don't need __setMovementTypeValue in this example) def __getattr__(self, name) : if name.startswith('Set') : movement = name.lstrip('Set') if movement in self.__controls : return lambda value : self.__controls[movement].SetValue(value) raise AttributeError That said, if I understand you well, your class RobotControl seems to contain only logic that is not specific to an instance, nor to a class of instances. In other OOP language I would encourage you to implement this logic in some sort of singleton, but in python we don't like this construct, module level variables and function do perfectly the job, simple as they are. 2.) What could I be doing wrong ? I have a suspicion that my error is not even related to all this fancy runtime code generation stuff, but something really dumb and I've just been coding for too long to see it. http://mail.python.org/pipermail/python-list/2007-June/446601.html shows a somewhat comparable constellation and it was a good guideline. But there, the function is created by the class factory, as well and I unfortunately can't do that. Thank you very much, Steve -- http://mail.python.org/mailman/listinfo/python-list -- _ Maric Michaud -- http://mail.python.org/mailman/listinfo/python-list
Re: generate methods at runtime, but the wrong one gets called
On Mon, 25 Aug 2008 12:52:44 +0200, Maric Michaud wrote: In other OOP language I would encourage you to implement this logic in some sort of singleton, but in python we don't like this construct, module level variables and function do perfectly the job, simple as they are. Modules are some sort of singletons in Python. Ciao, Marc 'BlackJack' Rintsch -- http://mail.python.org/mailman/listinfo/python-list