How to create functors?

R

Robert Dailey

Hello,

I want to simply wrap a function up into an object so it can be called
with no parameters. The parameters that it would otherwise have taken
are already filled in. Like so:


print1 = lambda: print( "Foobar" )
print1()

However, the above code fails with:

File "C:\IT\work\distro_test\distribute_radix.py", line 286
print1 = lambda: print( "Foobar" )
^
SyntaxError: invalid syntax

How can I get this working?
 
R

Robert Dailey

def print1():
    print "Foobar"

It looks like in your version of Python "print" isn't a function. It always
helps if you say the exact version you are using in your question as the
exact answer you need may vary.

I'm using Python 2.6. And using the legacy syntax in the lambda does
not work either. I want to avoid using a def if possible. Thanks.
 
R

Robert Dailey

def print1():
    print "Foobar"

It looks like in your version of Python "print" isn't a function. It always
helps if you say the exact version you are using in your question as the
exact answer you need may vary.

Seems like it works fine on everything else except for print(). For
example:

print1 = lambda: MyFunction( "FooBar" )

The syntax above is accepted by the interpreter.
 
C

Chris Rebert

I'm using Python 2.6. And using the legacy syntax in the lambda does
not work either. I want to avoid using a def if possible. Thanks.

chris@morpheus ~ $ python
Python 2.6.2 (r262:71600, May 14 2009, 16:34:51)
[GCC 4.0.1 (Apple Inc. build 5484)] on darwin
Type "help", "copyright", "credits" or "license" for more information. File "<stdin>", line 1
print1 = lambda: print( "Foobar" )
^
SyntaxError: invalid syntaxFoobar

Cheers,
Chris
 
R

Robert Dailey

I'm using Python 2.6. And using the legacy syntax in the lambda does
not work either. I want to avoid using a def if possible. Thanks.

chris@morpheus ~ $ python
Python 2.6.2 (r262:71600, May 14 2009, 16:34:51)
[GCC 4.0.1 (Apple Inc. build 5484)] on darwin
Type "help", "copyright", "credits" or "license" for more information.>>> print1 = lambda: print( "Foobar" )

  File "<stdin>", line 1
    print1 = lambda: print( "Foobar" )
                         ^
SyntaxError: invalid syntax>>> from __future__ import print_function
Foobar

Cheers,
Chris
--http://blog.rebertia.com

I see what you're saying now. However, why am I able to use print as a
function in general-purpose code in my Python 2.6 script, like so:

def SomeFunction():
print( "Hello World" )

But, I am not able to do this:

SomeFunction = lambda: print( "Hello World" )

??????

Doesn't make sense.
 
N

Ned Deily

I'm using Python 2.6. And using the legacy syntax in the lambda does
not work either. I want to avoid using a def if possible. Thanks.

The problem is that in Python 2 print is a statement, not a function.
That should work fine in Python 3 where print *is* a function. In 2.x,
you can wrap print in a function or use something like:
Foobar

or the pprint library module or various other solutions.
 
J

Jerry Hill

Hello,

I want to simply wrap a function up into an object so it can be called
with no parameters. The parameters that it would otherwise have taken
are already filled in. Like so:


     print1 = lambda: print( "Foobar" )
     print1()

However, the above code fails with:

 File "C:\IT\work\distro_test\distribute_radix.py", line 286
   print1 = lambda: print( "Foobar" )
                        ^
SyntaxError: invalid syntax

How can I get this working?

You can't, at least not with that example. Lambdas are restricted to
a single expression[1]. Print is not an expression, it's a
statement[2].

I'm guessing that your use case is not really in wrapping a print
statement in an anonymous function. Given the first part of your
message, you might find something of use in the functools module,
particularly functools.partial [3].

1: http://docs.python.org/tutorial/controlflow.html#lambda-forms
2: http://docs.python.org/reference/simple_stmts.html
3: http://docs.python.org/library/functools.html#functools.partial
 
R

Robert Dailey

Lambda expressions are, I believe, syntactically limited to a single  
expression -- no statements, like 'print' is in Python 2.x.

If you are strongly against just defining a function, you might have to  
use a trick to get around it -- this page  
(http://p-nand-q.com/python/stupid_lambda_tricks.html) has some  
suggestions.




--
Rami Chowdhury
"Never attribute to malice that which can be attributed to stupidity" --  
Hanlon's Razor
408-597-7068 (US) / 07875-841-046 (UK) / 0189-245544 (BD)

The example I gave earlier is a bit contrived, the real example
fundamentally requires a lambda since I am actually passing in local
variables into the functions the lambda is wrapping. Example:

def MyFunction():
localVariable = 20
CreateTask( lambda: SomeOtherFunction( localVariable ) ) # CreateTask
() executes the functor internally

This is more or less like the real scenario I'm working with. There
are other (more personal) reasons why I prefer to avoid 'def' in this
case. I want to keep the functor as central to the code that needs it
as possible to improve code readability.

Thanks for the help everyone. I guess in Python 3.0 the print()
function will not require the import from __future__ to work in this
particular case?
 
J

Jan Kaliszewski

18-08-2009 o 22:32:55 Robert Dailey said:
I'm using Python 2.6. And using the legacy syntax in the lambda does
not work either.

In Python 1.x/2.x 'print' is a keyword-based statement, not a function
-- then you cannot use it in lambda (which in Python is limited to
single expressions, and statements are not allowed in it).

You can try using sys.stdout.write() instead.
I want to avoid using a def if possible.

But what for? Usualy def is more readable than lambda and it's not worth
to lose readibility just to save a few keystrokes.

Cheers,
*j
 
R

Robert Dailey

In Python 1.x/2.x 'print' is a keyword-based statement, not a function
-- then you cannot use it in lambda (which in Python is limited to
single expressions, and statements are not allowed in it).

You can try using sys.stdout.write() instead.


But what for? Usualy def is more readable than lambda and it's not worth
to lose readibility just to save a few keystrokes.

Cheers,
*j

I posted a bit earlier than you did. See my previous post. Thanks for
the help.
 
R

Rami Chowdhury

why am I able to use print as a
function in general-purpose code in my Python 2.6 script

I believe it's because that is parsed as the print statement followed by a
parenthesized expression.

I want to simply wrap a function up into an object so it can be called
with no parameters. The parameters that it would otherwise have taken
are already filled in. Like so:
      print1 = lambda: print( "Foobar" )
      print1()
However, the above code fails with:
  File "C:\IT\work\distro_test\distribute_radix.py", line 286
    print1 = lambda: print( "Foobar" )
                         ^
SyntaxError: invalid syntax
How can I get this working?
def print1():
    print "Foobar"
It looks like in your version of Python "print" isn't a function. It always
helps if you say the exact version you are using in your question as the
exact answer you need may vary.
I'm using Python 2.6. And using the legacy syntax in the lambda does
not work either. I want to avoid using a def if possible. Thanks.

chris@morpheus ~ $ python
Python 2.6.2 (r262:71600, May 14 2009, 16:34:51)
[GCC 4.0.1 (Apple Inc. build 5484)] on darwin
Type "help", "copyright", "credits" or "license" for more
information.>>> print1 = lambda: print( "Foobar" )

  File "<stdin>", line 1
    print1 = lambda: print( "Foobar" )
                         ^
SyntaxError: invalid syntax>>> from __future__ import print_function
print1 = lambda: print( "Foobar" )
print1()

Foobar

Cheers,
Chris
--http://blog.rebertia.com

I see what you're saying now. However, why am I able to use print as a
function in general-purpose code in my Python 2.6 script, like so:

def SomeFunction():
print( "Hello World" )

But, I am not able to do this:

SomeFunction = lambda: print( "Hello World" )

??????

Doesn't make sense.
 
N

Ned Deily

I see what you're saying now. However, why am I able to use print as a
function in general-purpose code in my Python 2.6 script, like so:

def SomeFunction():
print( "Hello World" )

For the same reason you can do this:
<type 'str'>
 
J

Jan Kaliszewski

Dnia 18-08-2009 o 22:42:59 Robert Dailey said:
I see what you're saying now. However, why am I able to use print as a
function in general-purpose code in my Python 2.6 script, like so:

def SomeFunction():
print( "Hello World" )

But, I am not able to do this:

SomeFunction = lambda: print( "Hello World" )

??????

Because (unless you do 'from __future__ import print_function' in Py2.6)
it's statement, not a functions. In Python you can put any expression
in parentheses -- it's useful for wraping long lines but changes nothing
semantically (unless you add a comma -- then you create a tuple, even
without parentheses, but it'a another story...).

*j
 
R

Robert Dailey

Because (unless you do 'from __future__ import print_function' in Py2.6)
it's statement, not a functions. In Python you can put any expression
in parentheses -- it's useful for wraping long lines but changes nothing
semantically (unless you add a comma -- then you create a tuple, even
without parentheses, but it'a another story...).

*j

Ah, I see now. I completely fooled myself. This whole time I thought
Python 2.6 was updated to work with both forms of print by default as
a convenience, but still maintain the backwards compatibility.

I understand the situation now. Thanks to everyone for the help.
 
R

Rami Chowdhury

The example I gave earlier is a bit contrived, the real example
fundamentally requires a lambda since I am actually passing in local
variables into the functions the lambda is wrapping. Example:

def MyFunction():
localVariable = 20
CreateTask( lambda: SomeOtherFunction( localVariable ) ) # CreateTask
() executes the functor internally

This is more or less like the real scenario I'm working with.

You could define a local function ('closure') inside the function:

def MyFunction():
localVariable = 20
def UseLocalVariable():
SomeOtherFunction(localVariable)
CreateTask(UseLocalVariable)

I would suggest this is much better for readability.
 
L

Leonhard Vogt

The example I gave earlier is a bit contrived, the real example
fundamentally requires a lambda since I am actually passing in local
variables into the functions the lambda is wrapping. Example:

def MyFunction():
localVariable = 20
CreateTask( lambda: SomeOtherFunction( localVariable ) ) # CreateTask
() executes the functor internally

This is more or less like the real scenario I'm working with. There
are other (more personal) reasons why I prefer to avoid 'def' in this
case. I want to keep the functor as central to the code that needs it
as possible to improve code readability.

what about

def MyFunction():
localVariable = 20
def wrapper():
return SomeOtherFunction( localVariable )
CreateTask( wrapper )

the wrapper is only visible inside MyFunction.

Leonhard
 
D

Diez B. Roggisch

The example I gave earlier is a bit contrived, the real example
fundamentally requires a lambda since I am actually passing in local
variables into the functions the lambda is wrapping. Example:


funcs = []

for i in xrange(10):

def f(i=i):
print i

funcs.append(f)

for f in funcs:
f()

This is more or less like the real scenario I'm working with. There
are other (more personal) reasons why I prefer to avoid 'def' in this
case. I want to keep the functor as central to the code that needs it
as possible to improve code readability.

Didn't you say the other day you came from C++? Given the galactic
amount of hoops to jump through that language has to offer, typing

def f

instead of the even longe

lambda

strikes me as rather peculiar.

Diez
 
J

Jan Kaliszewski

Dnia 18-08-2009 o 22:51:19 Robert Dailey said:
The example I gave earlier is a bit contrived, the real example
fundamentally requires a lambda since I am actually passing in local
variables into the functions the lambda is wrapping. Example:

def MyFunction():
localVariable = 20
CreateTask( lambda: SomeOtherFunction( localVariable ) ) # CreateTask
() executes the functor internally

Lambda in Python is a sintactic sugar for some simple situations. But you
*always* can replace it with def, e.g.:

def MyFunction():

localVariable = 20
def TaskFunction():
SomeOtherFunction(localVariable)

CreateTask(TaskFunction)

If we say about You can also use functools.partial:

import functools

def MyFunction():

localVariable = 20
CreateTask(functools.partial(SomeOtherFunction, localVariable)

....which (especially) makes sense if passed function is supposed to be
callend many times.
This is more or less like the real scenario I'm working with. There
are other (more personal) reasons why I prefer to avoid 'def' in this
case. I want to keep the functor as central to the code that needs it
as possible to improve code readability.

IMHO def is mostly more readable (see my previous mail...).
Thanks for the help everyone. I guess in Python 3.0 the print()
function will not require the import from __future__ to work in this
particular case?

Print as a function is a standard feature of Py 3.x so it doesn't
require it (see: http://docs.python.org/3.1/whatsnew/3.0.html ).

Regards,
*j
 
R

Robert Dailey

Lambda in Python is a sintactic sugar for some simple situations. But you
*always* can replace it with def, e.g.:

  def MyFunction():

      localVariable = 20
      def TaskFunction():
          SomeOtherFunction(localVariable)

      CreateTask(TaskFunction)

If we say about You can also use functools.partial:

  import functools

  def MyFunction():

      localVariable = 20
      CreateTask(functools.partial(SomeOtherFunction, localVariable)

...which (especially) makes sense if passed function is supposed to be
callend many times.

Good point, I'm too used to C++ (Can't define functions in local
scope). I never thought of that. In C++ I use boost::bind() fairly
extensively and I carry over those habits to python.
IMHO def is mostly more readable (see my previous mail...).

Print as a function is a standard feature of Py 3.x so it doesn't
require it (see:http://docs.python.org/3.1/whatsnew/3.0.html).

Thanks for the info.
 
T

Terry Reedy

Robert said:
I'm using Python 2.6. And using the legacy syntax in the lambda does
not work either. I want to avoid using a def if possible. Thanks.

In Python, writing

name = lambda arg: expr

instead of

def name(arg): return expr

is all negative and no positive and should be avoided.

Your experience illustrates one reason why.

tjr
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
474,199
Messages
2,571,045
Members
47,643
Latest member
ashutoshjha_1101

Latest Threads

Top