Many types of optics have a van Laarhoven representation.
For example, a Lens of type Lens s t a b can be represented as:
Functor f => (a -> f b) -> s -> f t
Similarly a Traversal, can be represented in a similar way, swapping the Functor constraint for Applicative:
Applicative f => (a -> f b) -> s -> f t
Several optics frameworks, such as Monocle and Arrow define a type called Optional.
In Monocle's Optics heirarchy Optional fits between Lens and Traversal
As I understand it: If a Traversal is like a Lens that may have zero to many targets, then an Optional is like a Lens that may have zero to one targets.
In Monocle, Optional is defined as a pair of functions:
getOrModify :: s -> Either t a
set :: (b, s) -> t
Comments in the Monocle source code suggest that it's also possible to represent an Optional "as a weaker PLens and weaker PPrism"
Is it possible to represent an Optional as a van Laarhoven function?
There would be a way to represent it if the Functor/Applicative/Monad hierarchy were more fine-grained. In particular:
class Functor f => Pointed f where
pure :: a -> f a
type Optional s t a b = forall f. Pointed f => (a -> f b) -> s -> f t
Note that the type would probably be named Affine in the lens library if that was neatly in the class hierarchy.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With