getattr() on nested functions?

Gabriel Rossetti gabriel.rossetti at arimaz.com
Thu Aug 21 07:16:20 EDT 2008


Terry Reedy wrote:
>
>
> Gabriel Rossetti wrote:
>> Bruno Desthuilliers wrote:
>>> Gabriel Rossetti a écrit :
>
>>>> I thought that since functions are objects, that I could obtain 
>>>> it's nested functions.
>>>
>>> Well, there's probably a very hackish way, but it's not worth the pain.
>
> What Bruno meant here, I believe, is that there is probably a hackish 
> way to get the nested functions, but it indeed would not be worth the 
> pain.
Yes, I understood that :-)
>
> >>  The fact that functions are objects doesn't make nested
>>> functions methods of that object.
>
> A def statement is ultimately an assignment statement.  The name of 
> the nested function is a local variable just like any other local name.
>
Ok
> >> If what you really want are methods,
>>> then you can write your own callable:
>>>
>>> class _Test(object):
>>>   def request(self, params):
>>>       pass
>>>   def submit(self, params, values):
>>>       pass
>>>   def update(self, params, values):
>>>       pass
>>>   def delete(self, params):
>>>       pass
>>>   def __call__(self, action, *args):
>>>       return resultToXml(getattr(self, action)(*args))
>>>
>>> _test = _Test()
>>>
>> Yes, very hackish :-)
>
> No, not at all hackish, but one standard way to do what you want.
>
>>> locals() is your friend.
>>>
>>> def _test(self, action, *args):
>>>        def request(params):
>>>            pass
>>>        def submit(params, values):
>>>            pass
>>>        def update(params, values):
>>>            pass
>>>        def delete(params):
>>>            pass
>>>        result = locals()[action](*args)
>>>        return resultToXml(result)
>>>
>>>
>> Ok, thanks, that works :-), like I told Gabriel G., I keep on 
>> forgetting locals() exists :-)
>
> Unlike the class approach, this requires recreating the constant 
> functions and dict with each call to _test.  Quick to write but a bit 
> 'dirty', in my opinion.  Another standard idiom is to set up the 
> constants outside the function:
>
> def request(params):
>     pass
> def submit(params, values):
>     pass
> def update(params, values):
>     pass
> def delete(params):
>     pass
> dispatch = {'request':request, 'submit':submit, 'update':update, 
> 'delete':delete}
>
> def _test(self, action, *args):
>     return resultToXmo(dispatch[action](*args))

That's how I had done it originally (before the use of eval()), but in 
this case also, since the functions are still nested, they are 
re-created and so is the dict, so I don' t see a gain from the locals() 
method.
>
> Terry Jan Reedy
>
>
> -- 
> http://mail.python.org/mailman/listinfo/python-list



More information about the Python-list mailing list