I’m sure I’m missing something obvious, but here we go. I defined methods that dispatch on the type of various “special matrices” from LinearAlgebra. Here is a MWE:
using LinearAlgebra
for type ∈ [:Symmetric, :LowerTriangular]
@eval f(::Type{$type{T}}) where T = T
end
The expected result is returned when called on type LowerTriangular:
julia> f(LowerTriangular{Float64})
Float64
However, when called on Symmetric, I get:
julia> f(Symmetric{Float64})
ERROR: UndefVarError: T not defined
Stacktrace:
[1] f(#unused#::Type{Symmetric{Float64, S} where S<:(AbstractMatrix{<:Float64})})
@ Main ./REPL[5]:2
[2] top-level scope
@ REPL[10]:1
Interestingly, the following implementation works:
f(::Type{Symmetric{T, S}}) where {T, S} = T
julia> f(Symmetric{Float64, Matrix{Float64}})
Float64
using LinearAlgebra
for type ∈ [:Symmetric, :LowerTriangular]
@eval f(::Type{$type{T, A}}) where {T, A} = T
end
@show f(LowerTriangular{Float64,Matrix{Float64}})
@show f(Symmetric{Float64,Matrix{Float64}})
abstract type MyAbstractTriangular{S<:AbstractMatrix} <: AbstractMatrix{eltype(S)} end
is accepted.
Edit: this seems to work, too:
struct MyTriangularMatrix{S<:AbstractMatrix} <: MyAbstractTriangular{S}
A::S
end
function MyTriangularMatrix{T}(A::Matrix{T}) where T
end
tr = MyTriangularMatrix([(1, 2) (3, 4) (5, 6)])
println()