Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What does the Naturality law for Traversables mean?

The Naturality law states that:

t . traverse f == traverse (t . f) -- for every applicative transformer t

Now for the RHS of the law, if f has the type Applicative a => x -> a y, then t has to be of the type (Applicative a, Applicative b) => a y -> b y, due to the function composition.

For the LHS, traverse f has the type (Applicative a, Traversable c) => c x -> a (c y). But since traverse f is composed with t . traverse f, t has to be of the type (c x -> a (c y)) -> b y.

Now, for the LHS, t has the type a (c y) -> b y, but from the RHS it has the type a y -> b y. How is the law sound from a type perspective?

Edit: Fixed the type t in LHS

like image 274
user4132 Avatar asked Nov 24 '19 17:11

user4132


People also ask

What is the traversable Typeclass used for?

Traversable in Haskell unifies the concept of mapping over a container (getting a similary-shaped container in return) with the concept of "internal iterator" that performs an effect for each element.

What is traversable Haskell?

Advanced Haskell The fifth one is Traversable. To traverse means to walk across, and that is exactly what Traversable generalises: walking across a structure, collecting results at each stop.


1 Answers

I think what you have missed is that t is supposed to be a natural transformation (which also probably must have some structure-preserving properties). Natural transformations are quantified, like so:

t :: forall z. a z -> b z   -- "t is an N.T. from a ~> b"

On the right we instantiate it at y, to get t :: a y -> b y; on the left we instantiate it at c y to get a (c y) -> b (c y). The way I think of it is that a natural transformation changes the outer layer, no matter what is inside. Naturality laws always talk about relationships between the different ways something is instantiated.

t                :: forall z. a z -> b z

f                :: x -> a y
t                :: a y -> b y           -- instantiated at y
t . f            :: x -> b y
traverse (t . f) :: c x -> b (c y)

traverse f       :: c x -> a (c y)
t                :: a (c y) -> b (c y)   -- instantiated at (c y)
t . traverse f   :: c x -> b (c y)
like image 165
luqui Avatar answered Sep 28 '22 10:09

luqui