[Tutor] Passing functions as arguments to other functions

Alan Gauld alan.gauld at yahoo.co.uk
Fri Sep 30 04:43:47 EDT 2016


On 30/09/16 03:43, boB Stepp wrote:

> Also, I note that if I just type a function name without the
> parentheses in the interpreter, I will get something like this:
> 
>>>> def f():
>            pass
> 
>>>> f
> <function f at 0x000001F775A97B70>
> 
> So the impression I am getting is that a function name by itself (with
> no parentheses) is the function *object*. 

No.
The function name is just a name like any other name in Python

foo = 42
bar = lambda x: x**2

foo and bar are both names. foo refers to the integer object 42
and bar refers to the function object x**2.

But they are just names and we can reassign them at any
time to any other kind of object.

So in your example f is not the function object it is a
reference to a function object.

> But why does Python require separating the function object 
> from its parameters when it is being passed as an argument
> to another function?

g = f

causes g to become a second reference to the function object

g = f(x)

causes g to become a reference to the result of calling
the function object referred to by f, passing in the object
referred to by x.

The parentheses in this case are not there as a container
of the object x they are there as an indication that f
is being called.

Now let us assume that f doesn't care what kind of object
x is it would be perfectly possible to pass f itself as
an argument to f():

g = f(f)

The mechanism is exactly the same as before:
It causes g to become a reference to the result of calling
the function object referred to by f, passing in the object
referred to by f - a function object in this case.

and again if we do

g = f(f())

we apply the same rules. The argument to the outer f
is the result of calling the inner f() and g gets
the result of calling f with that inner result. The
parens after a function name cause that function to
be executed and its result to be returned.

So python is not doing anything different to the "normal"
case when passing functions. They are treated just like
any other function call parameter, as an object.

BTW You don't have to pass the arguments as separate values.
You could use globals(but please don't!) or you could create
local values inside the containing function, or even
read them from a user:

def do_op(aFunc):
    x = int(input("type an integer: "))
    return aFunc(x)

do_op(lambda x: x**2)

or

def process_3_and_4(aFunc):
    return aFunc(3,4)

process_3_and_4(lambda x,y: x**y)

HTH

-- 
Alan G
Author of the Learn to Program web site
http://www.alan-g.me.uk/
http://www.amazon.com/author/alan_gauld
Follow my photo-blog on Flickr at:
http://www.flickr.com/photos/alangauldphotos




More information about the Tutor mailing list