`map2` combines two values already living in the same context with a binary function. Its result remains in that context: two `Option` values produce an `Option`, two parser results produce a parser result, and two state actions produce a state action. The combinator separates ordinary domain logic—such as a function taking two plain arguments—from the mechanics of failure, parsing, or state. section 4.3.2 section 11.2
For `Option`, `map2(a, b)(f)` yields `Some(f(aa, bb))` only when both inputs contain values; otherwise it yields `None`. This lifts an existing two-argument function without rewriting it to know about optional inputs. An implementation uses `flatMap` on the first option and `map` on the second, avoiding a nested `Option[Option[C]]`. section 4.3.2 section 4.6
Combining parsed insurance inputs
Convert an age and ticket count from strings into `Option[Int]`, then call `map2(optAge, optTickets)(insuranceRateQuote)`. The rate function still accepts two `Int` values; failed conversion is represented by `None` rather than changing that function or manually matching both options. section 4.3.2
For stateful actions, `map2` runs the first action with the initial state, runs the second with the state returned by the first, and combines their produced values. Keeping this state threading inside `map2` removes repeated RNG bookkeeping and makes the sequencing easier to inspect. section 6.8
def map2[A, B, C](ra: Rand[A], rb: Rand[B])(f: (A, B) => C): Rand[C] =
rng0 =>
val (a, rng1) = ra(rng0)
val (b, rng2) = rb(rng1)
(f(a, b), rng2)
This implementation makes the three state values explicit: the first action consumes `rng0`, the second consumes `rng1`, and the combined action returns `rng2`. section 6.8
The same shape recurs in parsers, generators, `Either`, and `State`. For parsers, `map2` can be defined through `product` followed by `map`; recursive parser uses may require its second parser argument to be nonstrict. For `Either`, it combines two `Right` values while preserving a `Left` failure. section 9.8 section 4.4
Use `map2` when both contextual computations are known before their results are combined:
- Combine independent `Option` lookups, such as a department and salary lookup for the same name. section 12.3.1
- Build `sequence` and `traverse` by folding contextual values with list cons as the combining function. section 4.6 section 6.8
- Combine parser results into lists or structured values, while deferring recursive parsers when necessary. section 9.8
`map2` expresses a fixed computation structure: it combines results of computations selected independently. When the result of the first computation determines which second computation to perform, use `flatMap` or `join` instead. This distinction motivates `map2` as a primitive of `Applicative`, while monads can derive it from `flatMap`. section 12.3.1 section 12.2
