I have heard julia has dispatch on values for symbols,
and so I use Val{:MySymbol}
.
But this doesn't seem to work:
julia> foo(x) = "other"
foo (generic function with 1 method)
julia> foo(x::Val{:zinger}) = "It was zinger"
foo (generic function with 2 methods)
julia> foo(:zinger)
"other"
Why isn't it outputting "It was zinger"?
Using all of a function's arguments to choose which method should be invoked, rather than just the first, is known as multiple dispatch.
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.
Method TablesEvery function in Julia is a generic function. A generic function is conceptually a single function, but consists of many definitions, or methods. The methods of a generic function are stored in a method table.
Method overloading is resolved at compile time. Multiple dispatch is resolved at runtime. When using double dispatch the called method depends on the actual type of receiver and arguments. Method overloading however, only allows the called method to depend on the declared type of the parameters.
See the Docs
Dispatching on values isn't magic. It uses the exact same mechanics as for dispatching on parametric types. So you need to pass in a instance parametric type which has that value as a type parameter if you want to dispatch on it.
In your question Val
is the parametric type -- and it exists just for this kind of thing.
So you need to have written:
julia> foo(Val{:zinger}())
"It was zinger"
If you wanted you could write an overload of foo
to automatically wrap up its arguments into a type parameter
julia> foo(x::Symbol) = foo(Val{x}())
foo (generic function with 3 methods)
julia> foo(:zinger)
"It was zinger"
However, this will cause a dynamic dispatch.
julia> @code_lowered foo(:zinger)
CodeInfo(:(begin
nothing
return (Main.foo)(((Core.apply_type)(Main.Val, x))())
end))
vs the fully realized at compile-time solution:
julia> @code_lowered foo(Val{:zinger}())
CodeInfo(:(begin
nothing
return "It was zinger"
end))
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With