473,574 Members | 2,981 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

"Updating" lambda functions

Hi,

I'm trying to write a Python function that parses
an expression and builds a function tree from it
(recursively).

During parsing, lambda functions for the the terms
and sub-expressions are constructed on the fly.
Now my problem is lazy evaluation. Or at least I
think it is. :-)

I need to "update" a lambda function, like this:

fu = lambda x: x
...
fu = lambda x: fu(x) + 17
...
fu = lambda x: fu(x) * 3

Of course that doesn't work, because fu is resolved
when the lambda is called, not when it's defined, so
I'll run into an endless recursion.

My current solution is to define a helper function
which passes the lambda through its argument:

def add_17 (fu):
return lambda x: fu(x) + 17

def mul_3 (fu):
return lambda x: fu(x) * 3

fu = lambda x: x
...
fu = add_17(fu)
...
fu = mul_3(fu)

That works, but it strikes me as unclean and ugly.
Is there a better way to do it?

Best regards
Oliver

--
Oliver Fromme, Konrad-Celtis-Str. 72, 81369 Munich, Germany

``All that we see or seem is just a dream within a dream.''
(E. A. Poe)
Jul 18 '05 #1
53 3637
On Thu, 16 Sep 2004 14:07:20 +0000, Oliver Fromme wrote:
I need to "update" a lambda function, like this:


That says you need to use classes, not lambda functions.
Jul 18 '05 #2
"Oliver Fromme" <ol**@haluter.f romme.com> wrote in message
news:2q******** *****@uni-berlin.de...

| That works, but it strikes me as unclean and ugly.
| Is there a better way to do it?

I don't like it either. Consider this:
composition = lambda f,g: lambda x: f(g(x))
add_17 = lambda x: x+17
mul_3 = lambda x: 3*x
fu = lambda x:x
fu(3) 3 fu = composition(add _17,fu)
fu(3) 20 fu = composition(mul _3,fu)
fu(3)

60
Jul 18 '05 #3
On 16 Sep 2004 14:07:20 GMT, Oliver Fromme <ol**@haluter.f romme.com> wrote:
Hi,

I'm trying to write a Python function that parses
an expression and builds a function tree from it
(recursively ).

During parsing, lambda functions for the the terms
and sub-expressions are constructed on the fly.
Now my problem is lazy evaluation. Or at least I
think it is. :-)

I need to "update" a lambda function, like this:

fu = lambda x: x
...
fu = lambda x: fu(x) + 17
...
fu = lambda x: fu(x) * 3

Of course that doesn't work, because fu is resolved
when the lambda is called, not when it's defined, so
I'll run into an endless recursion.

My current solution is to define a helper function
which passes the lambda through its argument:

def add_17 (fu):
return lambda x: fu(x) + 17

def mul_3 (fu):
return lambda x: fu(x) * 3

fu = lambda x: x
...
fu = add_17(fu)
...
fu = mul_3(fu)

That works, but it strikes me as unclean and ugly.
Is there a better way to do it?

Best regards
Oliver

--
Oliver Fromme, Konrad-Celtis-Str. 72, 81369 Munich, Germany

``All that we see or seem is just a dream within a dream.''
(E. A. Poe)


You could exploit the way functions become bound methods, e.g.,
fu = lambda x: x
fu = (lambda f,x: f(x) + 17).__get__(fu)
fu = (lambda f,x: f(x) * 3).__get__(fu)
fu(1) 54 fu(0) 51 fu(-15) 6 fu(-16) 3 fu(1,2) Traceback (most recent call last):
File "<stdin>", line 1, in ?
TypeError: <lambda>() takes exactly 2 arguments (3 given) fu <bound method ?.<lambda> of <bound method ?.<lambda> of <function <lambda> at 0x008FD8B0>>>

or, you could make a magic function-composing object with magic composing properties,
exploiting the method-making mechanism in a different way, e.g.,
class FC(object): ... def __setattr__(sel f, name, f):
... if not hasattr(self, name): self.__dict__[name] = [f]
... else: self.__dict__[name].append(f)
... def __getattribute_ _(self, name):
... if name == '__dict__': return object.__getatt ribute__(self, '__dict__')
... return type(self).__di ct__['_xfuns'].__get__(
... object.__getatt ribute__(self,n ame))
... def _xfuns(flist, x):
... for f in flist: x = f(x)
... return x
... fc = FC()
fc.fu = lambda x: x
fc.fu = lambda x: x + 17
fc.fu = lambda x: x * 3
fc.fu(1) 54 fc.fu(0) 51 fc.fu(-15) 6 fc.fu(1,2) Traceback (most recent call last):
File "<stdin>", line 1, in ?
TypeError: _xfuns() takes exactly 2 arguments (3 given) fc.bar = lambda x: x*3
fc.bar = lambda x: x+10
fc.bar(0) 10 fc.bar(2) 16 fc.fu(-18)

-3

All just to explore python's features, not to recommend specific uses ;-)

Regards,
Bengt Richter
Jul 18 '05 #4

"Oliver Fromme" <ol**@haluter.f romme.com> wrote in message
news:2q******** *****@uni-berlin.de...
fu = lambda x: x
fu = lambda x: fu(x) + 17

etc

I am curious if there is any reason other that habit carried over from
other languages to not write the above as

def fu(x): return x
def fu(x): return fu(x) + 17
etc

Granted, the latter takes 2 more keystrokes, but the resulting object gets
a proper .name attribute. And, of course, the def form is required for a
multiline body anyway.

(Note: I am not asking about the use of lambda *within* an expression or as
a return value, but only the immediate name-binding of the supposedly
anonymous function where one does not want anonymity.)

Terry J. Reedy

Jul 18 '05 #5
"Terry Reedy" <tj*****@udel.e du> wrote in message
news:ma******** *************** *************** @python.org...

| I am curious if there is any reason other that habit carried over from
| other languages to not write the above as
|
| def fu(x): return x
| def fu(x): return fu(x) + 17
| etc

In my interpreter (IDLE 1.0 on Windows 98) it causes an infinite regress.
Jul 18 '05 #6
Elaine Jackson <elainejackson7 355 <at> home.com> writes:

"Terry Reedy" <tjreedy <at> udel.edu> wrote in message
news:mailman.34 28.1095385637.5 135.python-list <at> python.org...

| I am curious if there is any reason other that habit carried over from
| other languages to not write the above as
|
| def fu(x): return x
| def fu(x): return fu(x) + 17
| etc

In my interpreter (IDLE 1.0 on Windows 98) it causes an infinite regress.


Yes, it will, exactly as the lambda version would have. (And all the
solutions suggested to you for the lambda form are equally applicable to the
def form.) The question is why use the lambda form when you *do* want to bind
your function to a name? Basically,

f = lambda args: body

is equivalent to

def f(args): body

except that the def body is a set of statements (so you have to use 'return'),
and the lambda body is a single expression.

Not that it's coming any time soon, but Python 3000 is supposed to remove
lambda functions, so when you really *do* want to bind a function to a name
(like in your case here), it would probably be a good habit to get into to use
defs instead.

Steve

Jul 18 '05 #7
On Fri, 17 Sep 2004 07:46:12 +0000 (UTC), Steven Bethard <st************ @gmail.com> wrote:
Elaine Jackson <elainejackson7 355 <at> home.com> writes:

"Terry Reedy" <tjreedy <at> udel.edu> wrote in message
news:mailman.34 28.1095385637.5 135.python-list <at> python.org...

| I am curious if there is any reason other that habit carried over from
| other languages to not write the above as
|
| def fu(x): return x
| def fu(x): return fu(x) + 17
| etc

In my interpreter (IDLE 1.0 on Windows 98) it causes an infinite regress.
Yes, it will, exactly as the lambda version would have. (And all the
solutions suggested to you for the lambda form are equally applicable to the
def form.) The question is why use the lambda form when you *do* want to bind
your function to a name? Basically,

f = lambda args: body

is equivalent to

def f(args): body

except that the def body is a set of statements (so you have to use 'return'),
and the lambda body is a single expression.

Yes, but

obj.f = lambda args: body

is possible without an intermediate local binding of f that might clobber a previous f, as in

def f(args): body
obj.f = f
del f # if you want to clean up. But better save the old f in that case?

I'd rather use lambda.

Not that it's coming any time soon, but Python 3000 is supposed to remove
lambda functions, so when you really *do* want to bind a function to a name
(like in your case here), it would probably be a good habit to get into to use
defs instead.

Well, if lambda is removed (or not ;-), I hope an anonymous def expression is allowed,
so we can write

obj.f = def(args):
body
or

obj.f = def(args): body

or

obj.f = (
def(args):
body
) # at or to the left of the def column, for final dedent without special ')' processing.
(where def body indentation is referenced from wherever the def is)

Regards,
Bengt Richter
Jul 18 '05 #8
Bengt Richter <bokr <at> oz.net> writes:
On Fri, 17 Sep 2004 07:46:12 +0000 (UTC), I wrote:

f = lambda args: body

is equivalent to

def f(args): body
Yes, but

obj.f = lambda args: body

is possible without an intermediate local binding of f that might clobber a
previous f


Yeah, I probably should have been clear about that. If 'f' is really just a
name (as it was in my example) the two syntaxes I gave are equivalent. If 'f'
really isn't just a name, then you do still want an anonymous function. In
the OP's example though, 'f' really was just a name.
Well, if lambda is removed (or not , I hope an anonymous def expression is
allowed...


Well, it's come up a number of times (one of the more recent is
http://mail.python.org/pipermail/pyt...e/226714.html), but it
doesn't seem like there was any agreement on (a) what it should look like, or
(b) why having such anonymous defs was such a gain over named defs. If you'd
like to champion a PEP about it... ;)

Steve
Jul 18 '05 #9

"Bengt Richter" <bo**@oz.net> wrote in message
news:ci******** *************** **@theriver.com ...
"Terry Reedy" <tjreedy <at> udel.edu> wrote in message
news:mailman.34 28.1095385637.5 135.python-list <at> python.org...

| I am curious if there is any reason other that habit carried over
from
| other languages to not write the above as
|
| def fu(x): return x
| def fu(x): return fu(x) + 17


obj.f = lambda args: body

is possible without an intermediate local binding of f that might clobber
a previous f, as in

def f(args): body
obj.f = f
del f # if you want to clean up. But better save the old f in that
case?

I'd rather use lambda.


Thanks. I had not thought of this variation. Similar would be
seq[n] = lambda <whatever>

Of course, I *might* prefer being able to write

def obj.f(params): <etc> # and
def seq[n](params): <etc>

Since def is effectively a binding statement, name to function object (like
import, name to module), these seem not entirely unreasonable to me.

Terry J. Reedy


Jul 18 '05 #10

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

5
2493
by: could ildg | last post by:
As there is already __init__, why need a __new__? What can __new__ give us while __init__ can't? In what situations we should use __new__? And in what situations we must use __new__? Can __new__ take the place of __init__? Thanks.
81
7249
by: Matt | last post by:
I have 2 questions: 1. strlen returns an unsigned (size_t) quantity. Why is an unsigned value more approprate than a signed value? Why is unsighned value less appropriate? 2. Would there be any advantage in having strcat and strcpy return a pointer to the "end" of the destination string rather than returning a
4
1449
by: tperri | last post by:
I've got a user table with a field called Online, and when a user logs in, I set a value in this column to indicate they are online. And in the same fashion, when they click the logout button, I update this same field to indicate they are offline. However, how do I handle this when a user just X's out of the browser without logging off? ...
7
16541
by: andrewfsears | last post by:
I have a question: I was wondering if it is possible to simulate the multiple constructors, like in Java (yes, I know that the languages are completely different)? Let's say that I have a class called "Point" which would have two values "x" and "y". Now, let's say if it were the Java version, I would want two constructors: one that...
6
7015
by: pooba53 | last post by:
I have a VB .NET application that is communicating properly with an Access DB. I have a slew of textbox controls bound to a dataset and when the application launches, the fields are correctly populated. If someone changes a value in one of the text boxes, I need to have a button capture the change and commit the update to Access. I know I'm...
6
2643
by: =?Utf-8?B?S2Fp?= | last post by:
Hi all, using AJAX Toolkit with vb.net 2.0 how could I make this "Updating..." Screen like e.g. on Codeplex when you click on the "Vote" button http://www.codeplex.com/AtlasControlToolkit/WorkItem/View.aspx?WorkItemId=9124 ? So the whole screen becomes inactive and a small window says "Updating..." so the user knows that something is going...
29
1980
by: not.here.now | last post by:
A quick search of this group and its FAQ, and elsewhere, have not answered this question to my satisfaction. Apologies if I missed something obvious, either in the literature or my reasoning. Can someone tell me why "->" exists? The compiler knows the difference between a structure and a pointer to a structure, so why can't it just let me...
2
1953
by: Mike Gleason jr Couturier | last post by:
In VS Studio 2008, when I'm opening the "Pending Checkins" tab, the content is stuck with "Updating..." and never shows the checked-out files... Any ideas!? I'm doing my check-ins directly in sourcesafe. Every other ss commands are working in VS Studio 2K8 Thanks
2
361
by: Joe Strout | last post by:
On Nov 13, 2008, at 11:15 AM, J. Cliff Dyer wrote: Right, though the hasattr() check I put in my version of this approach takes care of that. Now THAT is something that hadn't occurred to me! I haven't really studied decorators yet (and I'm pretty sure Python didn't have them when I was last into it a decade ago). This is an...
0
7841
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However, people are often confused as to whether an ONU can Work As a Router. In this blog post, we’ll explore What is ONU, What Is Router, ONU & Router’s main...
0
8105
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. ...
1
7859
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For...
0
8137
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each protocol has its own unique characteristics and advantages, but as a user who is planning to build a smart home system, I am a bit confused by the...
0
6514
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing, and deployment—without human intervention. Imagine an AI that can take a project description, break it down, write the code, debug it, and then...
0
3774
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in...
0
3793
by: adsilva | last post by:
A Windows Forms form does not have the event Unload, like VB6. What one acts like?
1
2274
by: 6302768590 | last post by:
Hai team i want code for transfer the data from one system to another through IP address by using C# our system has to for every 5mins then we have to update the data what the data is updated we have to send another system
1
1369
muto222
by: muto222 | last post by:
How can i add a mobile payment intergratation into php mysql website.

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.