julia
julia copied to clipboard
Subtyping distributivity fails with diagonal typevar
I believe this should report true:
julia> (Tuple{T,T} where T<:Union{Int32,Int64}) == Union{Tuple{Int32,Int32},Tuple{Int64,Int64}}
false
Interestingly, making the union larger does make it distribute eventually:
julia> A = Union{Tuple{T,T} where T<:Union{Int32,Int64},Tuple{Int32,Int64},Tuple{Int64,Int32}};
julia> B = Tuple{Union{Int32,Int64},Union{Int32,Int64}};
julia> A == B
true
Reproduces on Julia 1.8 (and also 1.9 and master):
julia> versioninfo()
Julia Version 1.8.5
Commit 17cfb8e65ea (2023-01-08 06:45 UTC)
Platform Info:
OS: macOS (x86_64-apple-darwin21.4.0)
CPU: 8 × Intel(R) Core(TM) i7-1068NG7 CPU @ 2.30GHz
WORD_SIZE: 64
LIBM: libopenlibm
LLVM: libLLVM-13.0.1 (ORCJIT, icelake-client)
Threads: 1 on 8 virtual cores
Something similar with T in an invariant position:
julia> supertype(Int64)
Signed
julia> (Ref{T} where Int64<:T<:Signed) == Union{Ref{Int64},Ref{Signed}}
false
Or combining both of these quirks:
julia> (Tuple{T,T} where Int64<:T<:Any) == Tuple{Int64, Int64}
false
These should probably also be true, since T >: lb closes the UnionAll range (if I've thought it through correctly)
Edit: There are also examples without lower bounds:
julia> Union{Ref{Union{Int,String}}, Ref{<:Int}, Ref{<:String}} == Ref{<:Union{Int,String}}
false
UnionAlls and Unions are not equal, even if their effective extent may be, no? This is the same case, and I wouldn't necessarily expect them to be equal, since one is a type variable and the other a type:
julia> (Ref{T} where T<:Int) == Ref{Int}
false