Reputation: 125
I'm exploring Julia so I'm a newbie. Now I'm exploring its strongly typed features. What I'm realizing is that I can't see the usage of abstract types for arrays. Let me explain with an example:
Let's suppose that I would like to create a function which accepts arrays of reals, no matter its concrete type. I would use:
function f(x::Array{Real})
# do something
end
This function can be never called without raising a f has no method matching f(::Array{Float64,1})
I would like to call f([1,2,3])
or f([1.,2.,3.])
as long as the type of the element is Real.
I've read that you could promote or convert the array (p.eg f(convert(Array{Real}, [1, 2, 3]))
or so) but I see that way really non-dynamic and tedious.
Is there any other alternative rather than getting rid of the strongly typed behaviour?
Thanks.
Upvotes: 6
Views: 3577
Reputation: 1118
Since there's been an updated since the orginal answer, the keyword typealias
is gone so that the solution of @Matt B. would now be
const RealArray{T<:Real} = Array{T}
f(x::RealArray) = "do something with $x"
I'll just put this here for the sake of completeness ;)
Upvotes: 4
Reputation: 51
You can do this explicitly using the <:
subtype operator:
function f(x::Array)
return zero.(x)
end
function f(x::Array{<:Real})
return one.(x)
end
@show f([1, 2])
@show f([1.0, 2.0])
@show f([1im, 2im])
prints
f([1, 2]) = [1, 1]
f([1.0, 2.0]) = [1.0, 1.0]
f([1im, 2im]) = Complex{Int64}[0+0im, 0+0im]
Upvotes: 0
Reputation: 31342
To expand upon the solution by @user3580870, you can also use a typealias
to make the function definition a little more succinct:
typealias RealArray{T<:Real} Array{T}
f(x::RealArray) = "do something with $x"
And then you can use the typealias in anonymous functions, too:
g = (x::RealArray) -> "something else with $x"
Upvotes: 8