scala either pattern match
Asked Answered
H

2

12

what is wrong in this piece of code?

(Left("aoeu")) match{case Right(x) => ; case Left(x) => }
<console>:6: error: constructor cannot be instantiated to expected type;
 found   : Right[A,B]
 required: Left[java.lang.String,Nothing]     

why the pattern matcher just doesn't skip the Right and examine Left?

Housefather answered 13/12, 2010 at 19:35 Comment(1)
Um, the compiler is telling you that some of your code is unreachable. That's a good thing, yes?Osculation
P
16

Implicit typing is inferring that Left("aoeu") is a Left[String,Nothing]. You need to explicitly type it.

(Left("aoeu"): Either[String,String]) match{case Right(x) => ; case Left(x) => }

It seems that pattern matching candidates must always be of a type matching the value being matched.

scala> case class X(a: String) 
defined class X

scala> case class Y(a: String) 
defined class Y

scala> X("hi") match {  
     | case Y("hi") => ;
     | case X("hi") => ;
     | }
<console>:11: error: constructor cannot be instantiated to expected type;
 found   : Y
 required: X
       case Y("hi") => ;
            ^

Why does it behave like this? I suspect there is no good reason to attempt to match on an incompatible type. Attempting to do so is a sign that the developer is not writing what they really intend to. The compiler error helps to prevent bugs.

Polyandrist answered 13/12, 2010 at 19:47 Comment(1)
I think you underemphasized the key point: the compiler was correctly pointing out that a portion of the code was unreachable. Yes, you can defeat that error, but you shouldn't.Ruffo
S
7
scala> val left: Either[String, String] = Left("foo")
left: Either[String,String] = Left(foo)

scala> left match {
     | case Right(x) => "right " + x
     | case Left(x) => "left " + x }
res3: java.lang.String = left foo
Sustentacular answered 13/12, 2010 at 19:50 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.