Module

Data.Profunctor.Strong

#Strong

class Strong :: (Type -> Type -> Type) -> Constraintclass (Profunctor p) <= Strong p  where

The Strong class extends Profunctor with combinators for working with product types.

first and second lift values in a Profunctor to act on the first and second components of a Tuple, respectively.

Another way to think about Strong is to piggyback on the intuition of inputs and outputs. Rewriting the type signature in this light then yields:

first ::  forall input output a. p input output -> p (Tuple input a) (Tuple output a)
second :: forall input output a. p input output -> p (Tuple a input) (Tuple a output)

If we specialize the profunctor p to the function arrow, we get the following type signatures, which may look a bit more familiar:

first ::  forall input output a. (input -> output) -> (Tuple input a) -> (Tuple output a)
second :: forall input output a. (input -> output) -> (Tuple a input) -> (Tuple a output)

So, when the profunctor is Function application, first essentially applies your function to the first element of a Tuple, and second applies it to the second element (same as map would do).

Members

Instances

#splitStrong

splitStrong :: forall p a b c d. Category p => Strong p => p a b -> p c d -> p (Tuple a c) (Tuple b d)

Compose a value acting on a Tuple from two values, each acting on one of the components of the Tuple.

Specializing (***) to function application would look like this:

(***) :: forall a b c d. (a -> b) -> (c -> d) -> (Tuple a c) -> (Tuple b d)

We take two functions, f and g, and we transform them into a single function which takes a Tuple and maps f over the first element and g over the second. Just like bi-map would do for the bi-functor instance of Tuple.

#(***)

Operator alias for Data.Profunctor.Strong.splitStrong (right-associative / precedence 3)

#fanout

fanout :: forall p a b c. Category p => Strong p => p a b -> p a c -> p a (Tuple b c)

Compose a value which introduces a Tuple from two values, each introducing one side of the Tuple.

This combinator is useful when assembling values from smaller components, because it provides a way to support two different types of output.

Specializing (&&&) to function application would look like this:

(&&&) :: forall a b c. (a -> b) -> (a -> c) -> (a -> (Tuple b c))

We take two functions, f and g, with the same parameter type and we transform them into a single function which takes one parameter and returns a Tuple of the results of running f and g on the parameter, respectively. This allows us to run two parallel computations on the same input and return both results in a Tuple.

#(&&&)

Operator alias for Data.Profunctor.Strong.fanout (right-associative / precedence 3)

Modules