5
votes

Suppose I have a series of functions with keyword arguments of different names

foo(x, y; a=1, b=2) = (a + b) / (x + y)
bar(x, y; c=3, d=4) = (x - y) * (c - d)

And suppose I have third function that takes a function as an argument. I want to be able to pass any keyword argument(s) through to one of the first two functions when calling this third function.

master(x, y; fun::Function=foo, args...) = fun(x, y, args...)

My problem arises when trying to call the master function using keyword arguments.

julia> master(pi, e, fun=bar)
-0.423310825130748

julia> master(pi, e, fun=bar, c=4)
ERROR: MethodError: `bar` has no method matching bar(::Irrational{:π}, ::Irrational{:e}, ::Tuple{Symbol,Int64})
Closest candidates are:
  bar(::Any, ::Any)

Is there a way to pass through the keyword arguments without having to iteratively check the argument names?

Please let me know if the question is unclear and I'd be happy to clarify. I've looked for other questions, but the solutions I've seen generally show how to grab the name-value pairs, not how to pass them through to other functions with keyword arguments

1
You need to put a ; before splatting the keyword arguments. So perhaps try this fun(x, y; args...)spencerlyon2
Huzzah! That's exactly what I needed, thank you so much and apologies if this was too simple a question. Honestly searched high and low and must have just missed that little detail.Jacob Amos

1 Answers

8
votes

To highlight the answer spencerlyon2 gave in his comment, my problem was using a comma (,) instead of a semicolon (;) to separate the keyword arguments when calling fun.

WRONG:

master(x, y; fun::Function=foo, args...) = fun(x, y, args...)

RIGHT:

master(x, y; fun::Function=foo, args...) = fun(x, y; args...)