Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Dispatching on arguments after the slurping operator (args...) in julia

How would you implement a function like this:

function foo(a,b...,c)
    println(a,b,c)
end
foo(2,3,3,"last")

=> a = 2 , b = (3,3) , c = "last"

I cannot use something like:

function foo(a,b...) 
    c = b[end]
    println(a,b,c)
end

Because I want to dispatch on c, i.e. I want to have methods:

foo(a,b...,c::Foo)

and

foo(a,b...,c::Bar)

Also I cant have something like this:

foo_wrapper(a,b...) = foo(a,b[1:end-1],b[end])

Because I also want to dispatch on foo in general.

Is this somehow posssible?

like image 428
ailuj Avatar asked Dec 18 '21 20:12

ailuj


People also ask

What does multiple dispatch mean in Julia?

Using all of a function's arguments to choose which method should be invoked, rather than just the first, is known as multiple dispatch.

What is Julia exclamation mark?

an exclamation mark is a prefix operator for logical negation ("not") a! function names that end with an exclamation mark modify one or more of their arguments by convention.

What is the type of a function in Julia?

Function is an abstract type. So for example Vector{Function} is like a Vector{Any} , or Vector{Integer} : Julia just can't infer the results.

Does Julia have syntax?

It is a purely syntactical transformation. if you will, i.e. the do block defines an anonymous function that is passed as the first argument. For this to work it is, of course, required that there exist a method of func that has a matching signature, for example func(f::Function, ...)


1 Answers

you can invert the order and then dispatch on an auxiliary function:

function foo(a,d...)
    c = last(d)
    b = d[begin:end-1]
    return _foo(a,c,b...)
end

function _foo(a,c::Int,b...)
    return c+1
end

function _foo(a,c::Float64,b...)
    return 2*c
end

in the REPL:

julia> foo(1,2,3,4,5,6)
7
julia> foo(1,2,3,4,5,6.0)
12.0

julia> foo(1,2,8.0)
16.0

julia> foo(1,90) #b is of length zero in this case
91
like image 153
longemen3000 Avatar answered Sep 22 '22 01:09

longemen3000