Skip to content

Commit 73214ff

Browse files
Update docs reference/spec of intersection/union types
1 parent a084779 commit 73214ff

File tree

4 files changed

+27
-18
lines changed

4 files changed

+27
-18
lines changed

compiler/src/dotty/tools/dotc/core/TypeComparer.scala

Lines changed: 2 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -2768,19 +2768,10 @@ class TypeComparer(@constructorOnly initctx: Context) extends ConstraintHandling
27682768
}
27692769

27702770
/** Try to distribute `&` inside type, detect and handle conflicts
2771+
* Note that an intersection cannot be pushed into an applied type, see tests/neg/i23435-min.
27712772
* @pre !(tp1 <: tp2) && !(tp2 <:< tp1) -- these cases were handled before
27722773
*/
27732774
private def distributeAnd(tp1: Type, tp2: Type): Type = tp1 match {
2774-
case tp1 @ AppliedType(tycon1, args1) if false =>
2775-
tp2 match {
2776-
case AppliedType(tycon2, args2)
2777-
if tycon1.typeSymbol == tycon2.typeSymbol && tycon1 =:= tycon2 =>
2778-
val jointArgs = glbArgs(args1, args2, tycon1.typeParams)
2779-
if (jointArgs.forall(_.exists)) (tycon1 & tycon2).appliedTo(jointArgs)
2780-
else NoType
2781-
case _ =>
2782-
NoType
2783-
}
27842775
case tp1: RefinedType =>
27852776
// opportunistically merge same-named refinements
27862777
// this does not change anything semantically (i.e. merging or not merging
@@ -2819,8 +2810,7 @@ class TypeComparer(@constructorOnly initctx: Context) extends ConstraintHandling
28192810
}
28202811

28212812
/** Try to distribute `|` inside type, detect and handle conflicts
2822-
* Note that, unlike for `&`, a disjunction cannot be pushed into
2823-
* a refined or applied type. Example:
2813+
* Note that a disjunction cannot be pushed into a refined or applied type. Example:
28242814
*
28252815
* List[T] | List[U] is not the same as List[T | U].
28262816
*

docs/_docs/reference/new-types/intersection-types-spec.md

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -46,11 +46,6 @@ A & B <: B A & B <: A
4646
In another word, `A & B` is the same type as `B & A`, in the sense that the two types
4747
have the same values and are subtypes of each other.
4848

49-
If `C` is a co- or contravariant type constructor, then `C[A] & C[B]` can be simplified using the following rules:
50-
51-
- If `C` is covariant, `C[A] & C[B] ~> C[A & B]`
52-
- If `C` is contravariant, `C[A] & C[B] ~> C[A | B]`
53-
5449
When `C` is covariant, `C[A & B] <: C[A] & C[B]` can be derived:
5550

5651
```

docs/_docs/reference/new-types/union-types-spec.md

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,30 @@ case _: (A | B) => ...
4646
A & (B | C) =:= A & B | A & C
4747
```
4848

49+
When `C` is covariant, `C[A] | C[B] <: C[A | B]` can be derived:
50+
51+
```
52+
A <: A B <: B
53+
---------- ---------
54+
A <: A | B B <: A | B
55+
---------------- ----------------
56+
C[A] <: C[A | B] C[B] <: C[A | B]
57+
-----------------------------------------
58+
C[A] | C[B] <: C[A | B]
59+
```
60+
61+
When `C` is contravariant, `C[A] | C[B] <: C[A & B]` can be derived:
62+
63+
```
64+
A <: A B <: B
65+
---------- ----------
66+
A & B <: A A & B <: B
67+
---------------- ----------------
68+
C[A] <: C[A & B] C[B] <: C[A & B]
69+
-----------------------------------------
70+
C[A] | C[B] <: C[A & B]
71+
```
72+
4973
From these rules it follows that the _least upper bound_ (LUB) of a set of types
5074
is the union of these types. This replaces the
5175
[definition of least upper bound in the Scala 2 specification](https://www.scala-lang.org/files/archive/spec/2.13/03-types.html#least-upper-bounds-and-greatest-lower-bounds).

tests/pos/reference/intersection-types.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ object t2 {
2626
}
2727

2828
val x: A & B = new C
29-
val ys: List[A & B] = x.children
29+
val ys: List[A] & List[B] = x.children
3030

3131
class C extends A with B {
3232
def children: List[A & B] = ???

0 commit comments

Comments
 (0)