You know how in ActionScript you can do functionRef.apply(thisObj, argumentsArray) if you need to call a function with a dynamic list of arguments? I was looking for a way to do this in Python and googled for "apply". Lo and behold, I found that it was deprecated.
Instead of using a separate function, you can simply pass in your arguments (and keyword arguments) to the function itself.
e.g., to call function add_numbers(first_number=a,second_number=b) with the list special_arguments=[2,2], you'd write:
add_numbers(*special_arguments)
And, for keyword arguments, where my_awesome_keyword_arguments = {'first_number':2, 'second_number':2}:
add_numbers(**my_awesome_keyword_arguments)
Finally, you can mix both positional and keyword arguments (say positional=[2] and keyword={'second_number':2}):
add_numbers(*positional, **keyword)
The crazy thing is that I've been using methods that use extended syntax for months now and yet I didn't actually grok exactly what was going on until today. Ah, I love it when something clicks. (And did I mention that the more I use Python, the more I love it?) :)
The Function.apply (is even easier) in Python article by Aral Balkan, unless otherwise expressly stated, is licensed under a Creative Commons Attribution-Noncommercial 2.0 UK: England License.
Hi Aral,
Note that in AS3 you can now pass a variable number of arguments to the function itself:
function passAnything(…statements):void {
trace(statements.length +”: “+ statements);
}
[Example borrowed from this AS3 tutorial by senocular]
widged:
In python can also do that by:
def func(*args):
# now `args` is a tuple
print length(args)
print args
@widged: Yep, but it’s not the same thing. That’s the way I’d been using extended call syntax in Python not understanding that you can also _call_ it via an argument object.
For it to be equivalent, we should be able to do the following in AS3 (based on your example):
args = [1,2,3]
myFunc = function(x,y,z){
trace(x + “, ” + y + “, ” + z)
}
myFunc(…args)
or, borrowing Python syntax: myFunc(*args)
We can’t do that yet in AS3.
That said, Python and AS3 are very similar in flavor (both dynamic languages) and we do have apply which does the same thing. I just find Python’s syntax more concise in this case and quite elegant.
The second part of the awesomeness is that if you want a function bound to a particular scope (thisObj) you only need to call thisObj.function(*args, **kwargs).
thisObj.function is always bound to the scope thisObj. You can also use an unbound method and bind it later by passing in an additional first argument for self, e.g.:
class Foo(object):
bar = “”
def __init__(self, bar):
self.bar = bar
def foo(self):
return self.bar
f = Foo(“bar”)
print “bound method Foo(‘bar’).foo() %s” % f.foo()
print “unbound method Foo.foo(f) %s” % Foo.foo(f)
Thanks! Been really useful.
I did not understand what you were saying at start. Here’s a little recap:
func(*[a, b])
func(a, b)
func(**{key: value})
func(key=value)