Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Does Julia have a strict subtype operator?

Tags:

types

julia

Question: Does Julia have a strict subtype operator?

Note: The operator <: is not a strict subtype operator, since Number <: Number evaluates to true. I am interested in an operator that would evaluate to false for Number <: Number but true for Int <: Number.

Possible use case: Consider a function defined:

MyFunc{T<:Union(Int, String)}(x::Array{T, 1}, y::Array{T, 1)})

Currently, the function constrains x and y to be arrays of the same type, where that type is Int, String, or Union(Int, String). But with a strict subtype operator, I could force the input arrays to be of type Int or String, and eliminate the (rather odd) Union(Int, String) scenario.

like image 449
Colin T Bowers Avatar asked Sep 30 '22 07:09

Colin T Bowers


1 Answers

I don't think there is such an operator in Julia, but it would probably be quite easy to write a function that does the same check:

strictSubType{T,U}(::Type{T}, ::Type{U}) = T <: U && T != U # note: untested!

However, I have to question your use case. If what you really want is something like

function my_func{T<:String}(x::Vector{T}, y::Vector{T})
    # handle strings
    # note that String is an abstract type, inherited by e.g. ASCIIString and UTF8String
end

function my_func(x::Vector{Int}, y::Vector{Int})
    # handle ints
    # note that Int is a concrete type (actually an alias for either Int32 or Int64,
    # depending on your platform) so no generic type parameter is necessary
end

then write that instead. If you have parts of the logic that can be shared, refactor it out into separate methods, where you can perhaps relax the type parameters (or omit them entirely).

Update, in response to your comment:

If the two methods should do exactly the same thing, then you're probably better off using duck typing, and simply not specifying the types of the function arguments at all:

funciton my_func(x, y)
    # handle ints, strings and anything else that supports things you need (e.g. > and <)
end

Julia will compile specific methods for each type combination you call things for, so you will still get just as fast code; if the function is type stable, then it will be fast for any combination (see the Julia docs for a more thorough explanation of how this works). If you want to make sure that the two arguments are vectors, and that they are of the same type, I'd recommend doing diagonal dispatch (also more thoroughly explained in the docs):

function my_func{T}(x::AbstractVector{T}, y::AbstractVector{T})
    # handle stuff
end

Note that I use AbstractVector rather than Vector - this allows using some other container type that also behaves like a vector with elements of type T, maximizing the usability of your function for other coders.

like image 78
Tomas Aschan Avatar answered Oct 11 '22 10:10

Tomas Aschan