Reputation: 53786
This code applies a function to List of Ints and sets each value in the List of Option with value 4 :
val l = List(1,2,3,4,5) //> l : List[Int] =
val v = 4 //> v : Int = 4
def g(v:Int) = List(v-1, v, v+1) //> g: (v: Int)List[Int]
l map (x => {f(x);}) //> res0: List[Option[Int]] = List(Some(4), Some(4), Some(4), Some(4), Some(4))
Signature of map :
def map[B, That](f: A => B)(implicit bf: CanBuildFrom[Repr, B, That]): That = {
Since B is the first type parameter (in map[B, That]) does this mean its typed to the prefix operand 'l' (List) ?
How is 'A' typed ? Does the scala compiler somehow check the type within the the List 'l' and infer that its of type Int ?
How is 'That' typed ?
Upvotes: 2
Views: 4337
Reputation: 7373
The simple signature for map
in a List[A]
is
def map[B](f: (A) ⇒ B): List[B]
which means that
A
is determined by the type parameter of the actual list
Int
for the example list l
B
is determined by the target type of the function f
passed as argument
Option[Int]
for the example function f: Int -> Option[Int]
The expanded signature is
def map[B, That](f: A => B)(implicit bf: CanBuildFrom[Repr, B, That]): That
which exist so that you can generically map between containers that can be traversed in some way, even when the target traversable has a different form than the original.
A specific example is traversing a
Map
as a container ofPairs
, with a mapping function that produces single values. The resulting traversable is not aMap
anymore, so theCanBuildFrom
implicit parameter is used to find "available representations" for the resulting object.
In this signature we have
Repr
as the type of the original traversed containerB
as the target type of the contained values, as in the simplified signatureThat
as the type of the target container, determined by the implicit existence of a CanBuildFrom
with the correct types at call siteUpvotes: 11