lens uses a van Laarhoven encoding, encoding lenses as functions. This means than not only do
lens lenses form a category, but they actually compose using standard function composition. In other words, they can compose using the old-fashioned
. operator, even before the
optics, in contrast, defines lenses using opaque newtypes. It should still be possible to get access to composition via the
. operator by defining a
Category instance. However,
optics doesn't do that, but instead defines a new
% composition operator. The docs have this to say:
The (.) operator from Control.Category cannot be used to compose optics [..] because it would not support type-changing optics or composing optics of different kinds.
optics must use a different composition operator (%). Optic does not quite form a Category, thanks to type-changing optics.
This leaves me very puzzled. It is well known that
lens' van Laarhoven lenses do support type-changing (polymorphic update), whilst still being a category by construction, via their underlying function type.
Can someone explain why it's impossible for
optics lenses to form a category, even though they are functionally equivalent to van Laarhoven?
Is it possible to define lenses more opaque than
lens whilst still forming a lawful category?