for comprehension
If a type has flatMap
and map
(or it has flatMap
and map
as its extension methods), you can use for
comprehension instead of using nested flatMap
s and map
.
flatMap
and map
In for
comprehension, <-
s (left arrows) are flatMap
except for the last one. The last <-
is map
.
for {
b <- foo(a)
c <- bar(b)
d <- baz(c)
} yield b + c + d + e
is equivalent to
foo(a).flatMap { b =>
bar(b).flatMap { c =>
baz(c).map { d =>
b + c + d + e
}
}
}
So
for {
b <- foo(a) // flatMap { b =>
c <- bar(b) // flatMap { c =>
d <- baz(c) // map { d =>
} yield b + c + d + e
for {
b <- foo(a)
c <- bar(b)
} yield b + c + d
is equivalent to
foo(a).flatMap { b =>
bar(b).map { c =>
b + c + d
}
}
So
for {
b <- foo(a) // fatMap { b =>
c <- bar(b) // map { c =>
} yield b + c + d
for {
b <- foo(a)
} yield b + c
is equivalent to
foo(a).map { b =>
b + c
}
So
for {
b <- foo(a) // map { b =>
} yield b + c
It means the following one is meaningless
for {
b <- foo(a)
} yield b
because it's equivalent to
foo(a).map { b =>
b
}
which does nothing.
So you can simply do this instead.
foo(a)
A single <-
in for
-comprehension could be flapMap
as well depending on the return type of the function.
for {
b <- foo(a)
} yield bar(b)
where bar(b)
returns the same type as foo(a)
's.
It is equivalent to
foo(a).flatMap { b =>
bar(b)
}
So
for {
b <- foo(a) // foo(a).flatMap { b =>
} yield bar(b)
If your for
-comprehension has only one <-
, you can simply use map
or flatMap
instead of for
-comprehension, as it doesn't add much readability for a single map
or flatMap
case.