Getting parameters of, and aliases for, any arbitrary type


and as always, thanks in advance for taking the time to read this post and help me out.

I’m back to toying around with (and hopefully learning) Julia. In order to get a better feel for the type system and the possibilities that the language offers, I’ve decided to implement a subtype tree printer (probably a fairly common thing for novices to do).

This is working fine, but it’s not showing all the info I’d like. Specifically, when a type takes parameters, it doesn’t list them; and when there’s aliases for a type, those don’t show up either.

To illustrate what I mean, let’s consider Array.

This type takes two parameters, and I’d like for my function to show something like Array{T, N} or Array{T, N} where {T, N} instead of just Array for the node in question. When I have some type for which I don’t know whether it has parameters, how many there are or what they are, how do I get this information programmatically?

Furthermore, there’s aliases: Vector{T} is an alias for Array{T, 1}, and Matrix{T} is an alias for Array{T, 2}, and I’d like to include these in my tree in a similar manner as I would include subtypes of Array (possibly in a way that’s visually distinct from true subtypes, but that’s another matter). To do this, I’d have to get all such aliases in a programmatic manner, but again — if I have some arbitrary type, how do I tell if there are aliases for what I’m tempted to call specializations of this type?

(And JBTW, I know there’s other tools for visualizing the Julia type tree already. I am trying to reinvent the wheel on purpose here — I believe that doing so, solving the problems you run into along the way, and asking for help when you encounter a problem you can’t solve is a great way to learn.)

I checked for relevant questions, performed a web search and also skimmed through the Julia documentation, but did not find anything apropos.

Thank you & all the best!

This is a hack and relies on undocumented and unstable behavior, because your usecase isn’t really meant to be supported AFAIK:

params(::Type{T}) where {T} = (T.parameters...,)
params(::T) where {T} = params(T)
julia> params([1,2,3])
(Int64, 1)

This is what I did to get the parameters of a type (Check Type has parameters field with an element by Zentrik · Pull Request #493 · JuliaDebug/Cthulhu.jl · GitHub). It might be useful to look into how print prints types as I believe there’s logic to deal with aliasing in there.

Here’s the relevant code

extract_inner_type(x) = nothing
extract_inner_type(::Type{Type{T}}) where T = T
1 Like

Also see Extracting the type parameter from a super-type

In particular, note that the parameters of a concrete type and of its (abstract) supertypes are not necessarily related.

Since this is in the “new to Julia” section, I’ll also point to the subtypes and supertypes functions in the standard library, although I guess you already know about those.

Perhaps some user package (check JuliaHub) offers this functionality, however I guess you could just check each element in the collection returned by varinfo.