You don't have to use *
and **
explicitly. Simply pass the tuple and the dict and let apply_async
unpack them:
from multiprocessing import Pool
def f(x, *args, **kwargs):
print x, args, kwargs
args, kw = (1,2,3), {'cat': 'dog'}
print "# Normal call"
f(0, *args, **kw)
print "# Multicall"
P = Pool()
sol = [P.apply_async(f, (x,) + args, kw) for x in range(2)]
P.close()
P.join()
for s in sol: s.get()
Output:
# Normal call
0 (1, 2, 3) {'cat': 'dog'}
# Multicall
0 (1, 2, 3) {'cat': 'dog'}
1 (1, 2, 3) {'cat': 'dog'}
Remember that in python's documentation, if a function accepts *args
and **kwargs
its signature explicitly states that:
the_function(a,b,c,d, *args, **kwargs)
In your case:
apply_async(func[, args[, kwds[, callback]]])
There are no *
there, hence args
is one argument, which is unpacked when calling func
and kwargs
is one argument and processed in the same way. Also note that it's not possible to have other arguments after **kwargs
:
>>> def test(**kwargs, something=True): pass
File "<stdin>", line 1
def test(**kwargs, something=True): pass
^
SyntaxError: invalid syntax