```
function get_typparam(::Type{X{Q1,Q2,Q3}}) where X where {Q1,Q2,Q3}
[Q1,Q2,Q3]
end
```

ERROR: TypeError: Type{…} expression: expected UnionAll, got TypeVar

Thanks

```
function get_typparam(::Type{X{Q1,Q2,Q3}}) where X where {Q1,Q2,Q3}
[Q1,Q2,Q3]
end
```

ERROR: TypeError: Type{…} expression: expected UnionAll, got TypeVar

Thanks

Not sure if that’s useful but I was trying to do similar gymnastics, asked a question on stackoverflow where it was kindly explained to me that something like this is the neat way of recovering the type of a struct:

```
struct Foo{T<:Real}
x::T
end
bar(f::Foo{T}) where T = T
bar(Foo(2.0)) # --> Float64
bar(Foo(2)) # --> Int
```

It can probably be done better but I thought it helped clarify types & multiple dispatch. (Apologies if that’s not at all what you’re trying to do)

I think `X`

as a fully unrestricted type is not possible,

If `X`

is the subtype of some abstract type that has the type parameters you are interested in you can

You can do something like

So you can do, if `X`

is always a subtype of `AbstractFoo{Q1,Q2,Q3}`

```
function get_typparam(::Type{X}) where {X <: AbstractFoo{Q1,Q2,Q3}} where {Q1,Q2,Q3}
[Q1,Q2,Q3]
end
```

I think.

(not tested)

You also get the type parameters of a type by inspecting the type variable itself:

```
function type_params(x::Type)
t = Base.unwrap_unionall(x) # unpack a unionall in case not all type parameters are specified
return (t.parameters...,) # convert to a regular tuple
end
# test case
struct X{A,B,C} end
x1 = X{Int}
x2 = x1{Real}
x3 = x2{3}
```

This prints

```
Main> type_params(x1)
(Int64, B, C)
Main> type_params(x2)
(Int64, Real, C)
Main> type_params(x3)
(Int64, Real, 3)
```

I did something like this once, that worked as well, not sure if this is what you’re trying to do though

```
eltypes(::Type{Cache{T, Dim, CC, CF}}) where {T, Dim, CC, CF} = (T, Dim,CC, CF)
eltypes(p) = eltypes(typeof(p))
```