summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPaul Phillips <paulp@improving.org>2011-08-07 04:38:42 +0000
committerPaul Phillips <paulp@improving.org>2011-08-07 04:38:42 +0000
commit6fe5754cec7f389477e5aa29ef527916d5d615d0 (patch)
treea50c8d472582656d346e7a422c4599d8a04b2a68
parent2b31bc81adfe6470e7da4546a4858482e8a5b61f (diff)
downloadscala-6fe5754cec7f389477e5aa29ef527916d5d615d0.tar.gz
scala-6fe5754cec7f389477e5aa29ef527916d5d615d0.tar.bz2
scala-6fe5754cec7f389477e5aa29ef527916d5d615d0.zip
Better error message for case class/object matc...
Better error message for case class/object match confusion. Closes SI-4879, no review.
-rw-r--r--src/compiler/scala/tools/nsc/typechecker/Infer.scala26
-rw-r--r--test/files/neg/bug414.check1
-rw-r--r--test/files/neg/bug4879.check13
-rw-r--r--test/files/neg/bug4879.scala15
4 files changed, 53 insertions, 2 deletions
diff --git a/src/compiler/scala/tools/nsc/typechecker/Infer.scala b/src/compiler/scala/tools/nsc/typechecker/Infer.scala
index b70f20ea89..354eb52913 100644
--- a/src/compiler/scala/tools/nsc/typechecker/Infer.scala
+++ b/src/compiler/scala/tools/nsc/typechecker/Infer.scala
@@ -1540,8 +1540,30 @@ trait Infer {
val pt1 = pt.instantiateTypeParams(ptparams, ptvars)
if (pat.tpe <:< pt1)
ptvars foreach instantiateTypeVar
- else
- error(pat.pos, "pattern type is incompatible with expected type"+foundReqMsg(pat.tpe, pt))
+ else {
+ val sym = pat.tpe.typeSymbol
+ val clazz = sym.companionClass
+ val addendum = (
+ if (sym.isModuleClass && clazz.isCaseClass && (clazz isSubClass pt1.typeSymbol)) {
+ // TODO: move these somewhere reusable.
+ val typeString = clazz.typeParams match {
+ case Nil => "" + clazz.name
+ case xs => xs map (_ => "_") mkString (clazz.name + "[", ",", "]")
+ }
+ val caseString = (
+ clazz.caseFieldAccessors
+ map (_ => "_") // could use the actual param names here
+ mkString (clazz.name + "(", ",", ")")
+ )
+ (
+ "\nNote: if you intended to match against the class, try `case _: " +
+ typeString + "` or `case " + caseString + "`"
+ )
+ }
+ else ""
+ )
+ error(pat.pos, "pattern type is incompatible with expected type"+foundReqMsg(pat.tpe, pt) + addendum)
+ }
}
object toOrigin extends TypeMap {
diff --git a/test/files/neg/bug414.check b/test/files/neg/bug414.check
index ec23e26337..91bb39caf2 100644
--- a/test/files/neg/bug414.check
+++ b/test/files/neg/bug414.check
@@ -1,6 +1,7 @@
bug414.scala:5: error: pattern type is incompatible with expected type;
found : object Empty
required: IntMap[a]
+Note: if you intended to match against the class, try `case _: Empty[_]` or `case Empty()`
case Empty =>
^
bug414.scala:7: error: type mismatch;
diff --git a/test/files/neg/bug4879.check b/test/files/neg/bug4879.check
new file mode 100644
index 0000000000..6b9e452109
--- /dev/null
+++ b/test/files/neg/bug4879.check
@@ -0,0 +1,13 @@
+bug4879.scala:6: error: pattern type is incompatible with expected type;
+ found : object C
+ required: C
+Note: if you intended to match against the class, try `case _: C` or `case C(_)`
+ case C => true
+ ^
+bug4879.scala:10: error: pattern type is incompatible with expected type;
+ found : object D
+ required: D[T,U,V]
+Note: if you intended to match against the class, try `case _: D[_,_,_]` or `case D(_,_,_)`
+ case D => true
+ ^
+two errors found
diff --git a/test/files/neg/bug4879.scala b/test/files/neg/bug4879.scala
new file mode 100644
index 0000000000..7d6561e9e0
--- /dev/null
+++ b/test/files/neg/bug4879.scala
@@ -0,0 +1,15 @@
+case class C(d: Double) { }
+case class D[T, U, V](bingo: Int, donkey: String, private val vegas: Set[A])(jehovah: Int) { }
+
+class A {
+ def f = (new C(5)) match {
+ case C => true
+ case _ => false
+ }
+ def g[T, U, V](x: D[T, U, V]) = x match {
+ case D => true
+ case _ => false
+ }
+}
+
+