lambda closure question

2005-02-18 Thread Ted Lilley
What I want to do is pre-load functions with arguments by iterating
through a list like so:

>>>class myclass:
...pass
>>>def func(self, arg):
...print arg
>>>mylist = ["my", "sample", "list"]
>>>for item in mylist:
...setattr(myclass, item, lamdba self: func(self, item))

This attaches a list of functions to the class, making them bound
methods when called from a class instance.  The functions are all
similar except that they know their name through the item argument.
The lambda takes the underlying function and preloads it with its name,
and since lambdas support closures, it remembers the item variable that
was used to create it when it is actually called like so:

>>>obj = myclass()
>>>obj.list()
list

That's great, since I can write a generic function that just needs to
know its name to make a slight modification to its behavior, then
attach it a bunch of times to a class under different names.

Unfortunately, it doesn't work.  It seems the closure keeps track of
the variable fed to it dynamically - if the variable changes after the
lambda is created, the lambda still references the _variable_ not the
original _value_ and so gets the new value like so:

>>>obj.sample()
list
>>>obj.my()
list

At least, that's the explanation I'm deducing from this behavior.
Assuming that's the way Guido intended it to be (about as dynamic as it
can get), I'm at a loss to do what _I_ want it to do.  In fact, I don't
think there's any way to generate the lambdas properly without coding
in the name as a literal string, since any attempt to use a variable
reference will always get modified as the loop iterates.

Am I missing something?  Help.

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: lambda closure question

2005-02-19 Thread Ted Lilley
Wow, a lot of great discussion.  Almost a bit too much for me to
grasp...I do see two or more nuggets that really address my issue.

As a side note, I'm familiar with the term currying from a friend who
learned ML and Scheme quite some time ago.  Not sure if that's the true
origin, but it was a sufficiently different context from Python (or at
least I thought) that I didn't want to rely on its meaning.  I was also
sufficiently unsure of it's _exact_ meaning, since we're talking about
two slightly different models, that I didn't want to use the term for
that reason as well.  It's gratifying to know that it was a relevant
concept afterall, the partial function application discussion
notwithstanding.  It's also gratifying to see such a strong community
versed in functional programming styles.  Although I've only started
working with FP in Python, it's been a useful tool for making my
programming simpler.

The first useful nugget is the crystalization method.  I spent some
time thinking about the problem after I posted it and came up with the
same workaround, in fact, the exact same syntax.  It's a bit inelegant,
but it gets the job done for what I want to do.  I won't even attempt
to take a position in the debate about whether Python should work by
default the way it does or the way I want to use it. ;)  Seems we have
well-spoken advocates for both sides.

The other nifty nugget is Kent's suggestion for using old-style Python
default arguments to capture the variable value.  Since it looks
slightly more elegant I'm going to give it a shot.

I have to say, I was happily surprised by the volume and quality of
response to my little issue.  Thanks everyone!

Ted

-- 
http://mail.python.org/mailman/listinfo/python-list


Re: lambda closure question

2005-02-19 Thread Ted Lilley
I replied a few minutes ago thanking everyone for their pointers.  Very
interesting reading.  I don't see my post yet, so I do hope it comes
through.  I'm using a new newsreading service and don't yet have
confidence in it.

In any case, the addition of the default-setting argument in the lambda
works famously and is only a slight modification to my code.  While I
don't think it's particularly intuitive (I would hate to be a
hypothetical programmer trying to puzzle out what my code does), it
gets the job done and is a heck of a lot easier than attaching the list
of attributes manually as I would've done without Python's FP
capabilities.

Thanks again,

Ted

-- 
http://mail.python.org/mailman/listinfo/python-list