Skip to content

Commit 6974d2a

Browse files
committed
Fix matching on top types
1 parent 2909603 commit 6974d2a

File tree

2 files changed

+10
-13
lines changed

2 files changed

+10
-13
lines changed

compiler/src/dotty/tools/dotc/transform/IsInstanceOfEvaluator.scala

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -136,13 +136,14 @@ class IsInstanceOfEvaluator extends MiniPhaseTransform { thisTransformer =>
136136
/** Check if the selector's potential type parameters will be erased, and if so warn */
137137
val selTypeParam = tree.args.head.tpe.widen match {
138138
case tp @ AppliedType(_, arg :: _) =>
139-
// If the type is `Array[X]` where `X` extends AnyVal or `X =:=
140-
// Any`, this shouldn't yield a warning:
141-
val isArray = tp.isRef(defn.ArrayClass)
142-
val unerased = arg.derivesFrom(defn.AnyValClass) || arg.isRef(defn.AnyClass)
143-
val hasAnnot = arg.hasAnnotation(defn.UncheckedAnnot)
144-
145-
if (!hasAnnot && !(isArray && unerased)) ctx.uncheckedWarning(
139+
// If the type is `Array[X]` where `X` extends AnyVal
140+
val anyValArray = tp.isRef(defn.ArrayClass) && arg.derivesFrom(defn.AnyValClass)
141+
// param is: Any | AnyRef | java.lang.Object
142+
val topType = defn.ObjectType <:< arg
143+
// has @unchecked annotation to suppress warnings
144+
val hasUncheckedAnnot = arg.hasAnnotation(defn.UncheckedAnnot)
145+
146+
if (!topType && !hasUncheckedAnnot && !anyValArray) ctx.uncheckedWarning(
146147
ErasedType(hl"""|Since type parameters are erased, you should not match on them in
147148
|${"match"} expressions."""),
148149
tree.pos

tests/repl/erasure.check

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -35,12 +35,6 @@ scala> def matchArray2[A](xs: Array[Any]) = xs match { case xs: Array[Int] => xs
3535
longer explanation available when compiling with `-explain`
3636
def matchArray2[A](xs: Array[Any]): [A] => (xs: Array[Any])Array[Int]
3737
scala> def matchArray3[A](xs: Array[A]) = xs match { case xs: Array[Int] => xs; case xs: Array[AnyRef] => ???; case xs: Array[Any] => ??? }
38-
-- [E035] Erased Type Unchecked Warning: <console> -----------------------------
39-
5 |def matchArray3[A](xs: Array[A]) = xs match { case xs: Array[Int] => xs; case xs: Array[AnyRef] => ???; case xs: Array[Any] => ??? }
40-
| ^
41-
| abstract type pattern is unchecked since it is eliminated by erasure
42-
43-
longer explanation available when compiling with `-explain`
4438
def matchArray3[A](xs: Array[A]): [A] => (xs: Array[A])Array[Int]
4539
scala> def matchArray4(xs: Array[Any]) = xs match { case xs: Array[Int] => xs; case xs: Array[A] => ???; case xs: Array[Any] => ??? }
4640
-- [E035] Erased Type Unchecked Warning: <console> -----------------------------
@@ -56,4 +50,6 @@ scala> def matchList1(xs: List[Any]) = xs match { case xs: List[Int @unchecked]
5650
def matchList1(xs: List[Any]): Nothing
5751
scala> def matchList2(xs: List[Any]) = xs match { case List() => ???; case _ => ??? }
5852
def matchList2(xs: List[Any]): Nothing
53+
scala> def matchList3(xs: Seq[_]) = xs match { case List() => ???; case _ => ??? }
54+
def matchList3(xs: Seq[_]): Nothing
5955
scala> :quit

0 commit comments

Comments
 (0)