Skip to content

Commit 70a49f9

Browse files
authored
Merge pull request #8390 from travisbrown/topic/deriving-adt-constructor-order
Specify order of MirroredElemTypes for Mirror.SumOf
2 parents cb61aca + ed9cb09 commit 70a49f9

File tree

2 files changed

+28
-0
lines changed

2 files changed

+28
-0
lines changed

docs/docs/reference/contextual/derivation.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -129,6 +129,10 @@ Note the following properties of `Mirror` types,
129129
Scala 2 versions of shapeless). Instead the collection of child types of a data type is represented by an ordinary,
130130
possibly parameterized, tuple type. Dotty's metaprogramming facilities can be used to work with these tuple types
131131
as-is, and higher level libraries can be built on top of them.
132+
+ For both product and sum types, the elements of `MirroredElemTypes` are arranged in definition order (i.e. `Branch[T]`
133+
precedes `Leaf[T]` in `MirroredElemTypes` for `Tree` because `Branch` is defined before `Leaf` in the source file).
134+
This means that `Mirror.Sum` differs in this respect from shapeless's generic representation for ADTs in Scala 2,
135+
where the constructors are ordered alphabetically by name.
132136
+ The methods `ordinal` and `fromProduct` are defined in terms of `MirroredMonoType` which is the type of kind-`*`
133137
which is obtained from `MirroredType` by wildcarding its type parameters.
134138

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
import scala.compiletime.erasedValue
2+
import scala.deriving.Mirror
3+
4+
object Test extends App {
5+
inline def checkElems[A, T](using inline A: Mirror.SumOf[A]): Unit =
6+
inline erasedValue[A.MirroredElemTypes] match {
7+
case _: T => ()
8+
}
9+
10+
sealed trait Base1
11+
case class Foo() extends Base1
12+
case object Bar extends Base1
13+
case class Qux(i: Int) extends Base1
14+
15+
checkElems[Base1, (Foo, Bar.type, Qux)]
16+
17+
enum Tree[+T] {
18+
case Empty
19+
case Branch[T](left: Tree[T], right: Tree[T]) extends Tree[T]
20+
case Leaf[T](elem: T) extends Tree[T]
21+
}
22+
23+
checkElems[Tree[String], (Tree.Empty.type, Tree.Branch[String], Tree.Leaf[String])]
24+
}

0 commit comments

Comments
 (0)