Erik Kaplun
Erik Kaplun

Reputation: 38207

Why type inference fails with Seq#collect in this case

The following

List(1, 2, 3).collect { x =>
  val dummy = ()
  x match { case _ => x }
}

results in

<console>:9: error: missing parameter type
                  List(1, 2, 3).collect { x =>

but this seemingly identical snippet works as expected:

List(1, 2, 3).collect { x =>
  x match { case _ => x }
}

It's true that collect takes a PartialFunction, but the way I see this is that if { x => x match { ... } } is PartialFunction (which must be due to a special case in the compiler because it looks just like a normal function that throws MatchError) then { x => smth(); x match { ... } } should also be a PartialFunction. (EDIT: I'm not sure even the first case is inferred to be a PartialFunction)

Upvotes: 1

Views: 45

Answers (1)

kiritsuku
kiritsuku

Reputation: 53348

This behavior is described in the Scala specification in section 8.5 Pattern Matching Anonymous Functions.

In short it means that an expression {x => x match { case ... => ... } }, which is an anonymous function, is implicitly converted to a PartialFunction when a PartialFunction is expected, as it is the case for collect.

The expression

{ x =>
  val dummy = ()
  x match { case _ => x }
}

is of different shape, thus it is not implicitly converted. It is treated as type A => B because it takes a value of type A and its body contains two expressions, namely val dummy = () and x match { case _ => x } where the latter produces a value of type B

Upvotes: 2

Related Questions