# Understanding Types Union{}

I read the manual about types carefully, but I can’t figure out how to do this.
Let’s two types of data are possible: `Vector{Int8}` and `Vector{Vector{Int8}}`
eg `[1, 0, 1]` and `[[1, 1], [0]]`

Following the recommendations, I wrote two implementations:
`some_calc(vec::Vector{Int8})` and
`some_calc(vec::Vector{Vector{Int8}})`

They both work efficiently and recognise types.
But there are actions that have to be done anyway,
so there is a main function that should accept both types:

``````main_calc(vec::???)
…
some_calc(vec)
…
end
``````

I tried to write `Vector` in place of ???, or just `vec` without type description -
nothing works. After studying the manual, I thought the right idea was
`Union{Vector{Int8}, Vector{Vector{Int8}}}`

But surprisingly

``````typeof([[1,2], [1,3]]) == Union{Vector{Int64}, Vector{Vector{Int64}}} → false
typeof([1,2,3]) == Union{Vector{Int64}, Vector{Vector{Int64}}} → false
``````

I’m tracking the conversion `Int64 → Int8` (it’s needed for performance, so there is no problem with it)
But the last results confused me!

PS. Why do I care so much about types? (Maybe it helps new users)
I do complex computations like fractal research.
And found that Julia is great for this, and with strict typing and right memory allocation much faster than Python etc. So Julia rocks!

1 Like

If it’s just a single method you could just declare it like `main_calc(vec)`, so without any type annotations. For more safety/strictness, you could use `main_calc(vec::Vector)`. For even more strictness, you could use union types: `main_calc(vec::Vector{<:Union{Int8,Vector{Int8}}})`.

1 Like

Thank you that’s work!

`typeof([1,2,3]) == Union{Vector{Int64}, Vector{Vector{Int64}}}` is false, because `Vector{Int64}` is not the same type as `Union{Vector{Int64}, ...}`. You can check for example

``````julia> isconcretetype(Union{Vector{Int64}, Vector{Vector{Int64}}})
false

julia> isconcretetype(Vector{Int64})
true
``````

The following holds though,

``````julia> Vector{Int64} <: Union{Vector{Int64}, Vector{Vector{Int64}}}
true
``````

as any type `T` is a subtype of a `Union` containing `T` or some supertype thereof.

Now, the type `Vector{<:Union{Int64,Vector{Int64}}}` is different as it specifies a vector where each element could be an `Int64` or a `Vector{Int64}`:

``````julia> Vector{<:Union{Int64,Vector{Int64}}} == (Vector{T} where {T <: Union{Int64, Vector{Int64}}})
true
julia> [1, 2, 3] isa Vector{<:Union{Int64,Vector{Int64}}}
true
julia> [1, 2, 3] isa Union{Vector{Int64},Vector{Vector{Int64}}}
true
# Note: [1, [2], 3] constructs a Vector{Any} thus explicit types are needed here
julia> Union{Int64, Vector{Int64}}[1, [2], 3] isa Vector{<:Union{Int64, Vector{Int64}}}
true
julia> Union{Int64, Vector{Int64}}[1, [2], 3] isa Union{Vector{Int64}, Vector{Vector{Int64}}}
false
``````

I.e., `Union{Vector{Int64}, Vector{Vector{Int64}}}` requires either a `Vector{Int64}` or `Vector{Vector{Int64}}`, but does not allow for mixed element types.