# Behaviour of nested alias type parameters

**URL:** <https://discourse.julialang.org/t/behaviour-of-nested-alias-type-parameters/15893>\
**Category:** New to Julia\
**Created:** [October 4, 2018, 6:06pm UTC](https://discourse.julialang.org/t/behaviour-of-nested-alias-type-parameters/15893 "2018-10-04T18:06:03Z")\
**Posts on this page:** 6\
**Page:** 1

<div class="post-metadata">

**Author:** ![balbasty](https://avatars.discourse-cdn.com/v4/letter/b/7cd45c/32.png) [@balbasty](https://discourse.julialang.org/u/balbasty)\
**Post date:** [October 4, 2018, 6:06pm UTC](https://discourse.julialang.org/t/behaviour-of-nested-alias-type-parameters/15893/1 "2018-10-04T18:06:03Z")

</div>

Hi all,

I am new to Julia and encountered a confusing result with nested `where` statements. However, I do not know if this is a bug or an intended (but ill-documented) behaviour. Here’s a snippet describing it:

```julia
julia> MyAlias{A,B} = Tuple{A,B} where {B,A}
Tuple{A,B} where A where B

julia> MyAlias{1,2}
Tuple{2,1}

```

I was expecting to get a `Tuple{1,2}`, as I thought that the only purpose of `where` was to annotate yet unknown parameters. Obviously, this is easily fixed by using parameters in the right order (`where {A,B}`), but still, it’s confusing.

This does not happen if I try to reproduce it with a function, so it might be a bug:

```julia
julia> myprint(::Tuple{A,B}) where {B,A} = print(A,B)
myprint (generic function with 1 method)

julia> myprint((1,1.0))
Int64Float64

```

I am using julia 1.0.0:

```julia
julia> versioninfo()
Julia Version 1.0.0
Commit 5d4eaca0c9 (2018-08-08 20:58 UTC)
Platform Info:
  OS: macOS (x86_64-apple-darwin14.5.0)
  CPU: Intel(R) Core(TM) i5-4258U CPU @ 2.40GHz
  WORD_SIZE: 64
  LIBM: libopenlibm
  LLVM: libLLVM-6.0.0 (ORCJIT, haswell)
Environment:
  JULIA_EDITOR = atom -a
  JULIA_NUM_THREADS = 2

```

---

<div class="post-metadata">

**Author:** ![ExpandingMan](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/expandingman/32/866_2.png) [@ExpandingMan](https://discourse.julialang.org/u/ExpandingMan)\
**Post date:** [October 4, 2018, 6:17pm UTC](https://discourse.julialang.org/t/behaviour-of-nested-alias-type-parameters/15893/2 "2018-10-04T18:17:07Z")

</div>

The precedence of `where` is indeed confusing, though as I recall, other choices led to some pretty strange behavior in function declarations.

What you’re supposed to do in this case is

```julia
const MyAlias{A,B} = Tuple{A,B}

```

without the `where`. I agree this is confusing. It’s probably legacy from when there used to be a `typealias` keyword. Essentially the `=` operator is special for type aliases.

Note also that `Tuple` is special in that it is the only [covariant type](https://en.wikipedia.org/wiki/Covariance_and_contravariance_(computer_science)) in the language.

I’m curious what opinion the core devs have on the lack of anything to indicate the fact that the type parameters are undefined variables lacking a `where` clause in these cases.

---

<div class="post-metadata">

**Author:** ![mauro3](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mauro3/32/292_2.png) [@mauro3](https://discourse.julialang.org/u/mauro3)\
**Post date:** [October 4, 2018, 6:32pm UTC](https://discourse.julialang.org/t/behaviour-of-nested-alias-type-parameters/15893/3 "2018-10-04T18:32:41Z")

</div>

The `A` and `B` left and right of the `=` are not related (this is not a function-like thing):

```julia
julia> MyAlias{X,Y} = Tuple{A,B} where {B,A}                                                                                                                            
Tuple{A,B} where A where B                                                                                                                                              

julia> MyAlias{1,2}                                                                                                                                                     
Tuple{2,1}   

```

What you wrote above is equivalent to (note the switch):

```julia
julia> MyAlias{X,Y} = Tuple{A,B} where A where B                                                                                                                        
Tuple{A,B} where A where B                                                                                                                                              

julia> MyAlias{1}                                                                                                                                                       
Tuple{A,1} where A                                                                                                                                                      

```

And that is indeed reversed from the parameters in the type. Hmm, this wasn’t that clear, sorry.

---

<div class="post-metadata">

**Author:** ![balbasty](https://avatars.discourse-cdn.com/v4/letter/b/7cd45c/32.png) [@balbasty](https://discourse.julialang.org/u/balbasty)\
**Post date:** [October 4, 2018, 6:56pm UTC](https://discourse.julialang.org/t/behaviour-of-nested-alias-type-parameters/15893/4 "2018-10-04T18:56:55Z")

</div>

Thanks a lot!

I did not realize that the `where` was not necessary in this case. It is indeed cleaner (and less error-prone) with this syntax.

There’s still some confusing stuff:

```julia
julia> Type1 = Tuple{A,B} where {A,B}
Tuple{A,B} where B where A

julia> Type2 = Tuple{A,B} where {B,A}
Tuple{A,B} where A where B

julia> Type1 == Type2
true

julia> Type1{1,2}
Tuple{1,2}

julia> Type2{1,2}
Tuple{2,1}

julia> Type1{1,2} == Type2{1,2}
false

```

---

<div class="post-metadata">

**Author:** ![mauro3](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mauro3/32/292_2.png) [@mauro3](https://discourse.julialang.org/u/mauro3)\
**Post date:** [October 4, 2018, 7:53pm UTC](https://discourse.julialang.org/t/behaviour-of-nested-alias-type-parameters/15893/5 "2018-10-04T19:53:07Z")

</div>

Yep, also this one:

```julia
julia> Type3{X,Y,Z} = Tuple{A,B} where {A,B}                                                                                                                            
Tuple{A,B} where B where A                                                                                                                                              

julia> Type3{2,3,4}                                                                                                                                                     
ERROR: too many parameters for type                                                                                                                                     
Stacktrace:
 [1] top-level scope at none:0

```

It looks like the parameters on the LHS are just ignored. Better would be to error if there are any parameters at all.

---

<div class="post-metadata">

**Author:** ![mauro3](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mauro3/32/292_2.png) [@mauro3](https://discourse.julialang.org/u/mauro3)\
**Post date:** [October 5, 2018, 10:13am UTC](https://discourse.julialang.org/t/behaviour-of-nested-alias-type-parameters/15893/6 "2018-10-05T10:13:16Z")

</div>

I filed issues [Type alias defs can contain parameters but they are just ignored · Issue #29533 · JuliaLang/julia · GitHub](https://github.com/JuliaLang/julia/issues/29533) and [UnionAll comparison does not take order of parameters into account · Issue #29534 · JuliaLang/julia · GitHub](https://github.com/JuliaLang/julia/issues/29534). Thanks @balbasty!
