packages feed

lens-family 1.2.3 → 2.0.0

raw patch · 7 files changed

+672/−268 lines, 7 filesdep ~basedep ~lens-family-coredep ~mtl

Dependency ranges changed: base, lens-family-core, mtl, transformers

Files

CHANGELOG view
@@ -1,46 +1,78 @@+2.0.0 (Changes from 1.2.4)+==========================+This new release continues to explore the design of Van Laarhoven style+optics with new support for adapters, grates, grids[2], and prisms.++To bring support to these new optics necessarily mean moving a little+further away from syntactic compatibility with Kmett's lens library.+In particular, lens-family's 'under' is unrelated to Kmett's lens+library's 'under' combinator.  Nonetheless the 'under' combinator plays+a crucial role in lens-family as a dual to the 'over' combinator and+this naming is hard to resist despite the conflict.++This new version comes with some minor incompatibilities with the version+1.0 library that may require user updates:++* 'backwards' has moved into the "Stock" module.+* '_Left' and '_Right' have been renamed as 'lft_' and 'rgt_'.+* '_Just' and '_Nothing' have been renamed as 'some_' and 'none_'.+* 'both' has been renamed 'both_'.+* 'beside' has been renamed 'beside_'.+* 'iso' has been removed, however its functionality can be replicated by+  a combination of 'adapter' and 'under'.++[1]<https://www.twanvl.nl/blog/haskell/cps-functional-references>+[2]A grid is an optic that is both a grate and a traversal.++1.2.4 (Changes from 1.2.3)+==========================+* Add 'matching' operator+* Correct lower bound on transformers+* Expand Applicative imports to broaden compatability+ 1.2.3 (Changes from 1.2.2)-=========================+========================== * Bump dependency on containers  1.2.2 (Changes from 1.2.1)-==========================-* Added strict versions of assignments to Lens.Family2.State modules.-* Added strict versions of at' and intAt'.-* Min dependencies raised to take advantage of adjustF from Data.Map.+===========================+* Added strict versions of assignments to Lens.Family2.State modules+* Added strict versions of at' and intAt'+* Min dependencies raised to take advantage of adjustF from Data.Map  1.2.1 (Changes from 1.2.0)-=========================+========================== * Bump dependency on transformers and mtl  1.2.0 (Changes from 1.1.0)-=========================-* Corrected associativity of ^. ^.. and ^? from right to left.+==========================+* Corrected associativity of ^. ^.. and ^? from right to left  1.1.0 (Changes from 1.0.1)-=========================-* Some type synonym definitions have been altered, but should be equivalent.-* Removed Getting and Setting functors and instead use the equivalent standard functors Const and Identity.-* Renamed Setter to ASetter and generalized Setters to be a LensLike constrained to an "Identical" functor.-* Added the (<~) operator.+==========================+* Some type synonym definitions have been altered, but should be equivalent+* Removed Getting and Setting functors and instead use the equivalent standard functors Const and Identity+* Renamed Setter to ASetter and generalized Setters to be a LensLike constrained to an "Identical" functor+* Added the (<~) operator * Corrected the definition of ATraversal'  1.0.1 (Changes from 1.0.0)-=========================+========================== * Bump dependency on transformers and mtl  1.0.0 (Changes from 0.1.0)-=========================+========================== * added support for folds and traversals-* renamed all functions to be mostly compatible with the lexicon from lens.+* renamed all functions to be mostly compatible with the lexicon from lens  0.1.0 (Changes from 0.0.1)-=========================+========================== * added project and sec * added <>= and <>~ * renamed functional modifier operators * moving setting to Lens.Family2.Unchecked because one needs to verify the functor laws  0.0.1 (Changes from 0.0.0)-=========================+========================== * Bump dependency on containers * Fixed dependency on mtl
lens-family.cabal view
@@ -1,41 +1,52 @@ name:               lens-family category:           Data, Lenses-version:            1.2.3+version:            2.0.0 license:            BSD3 cabal-version:      >= 1.6 license-file:       LICENSE author:             Russell O'Connor maintainer:         Russell O'Connor <roconnor@theorem.ca> stability:          experimental-copyright:          Copyright (C) 2012,2013,2014,2017 Russell O'Connor+copyright:          Copyright (C) 2012,2013,2014,2017,2018,2019 Russell O'Connor synopsis:           Lens Families build-type:         Simple extra-source-files: CHANGELOG-description:        This package provides first class functional references.-                    In addition to the usual operations of getting, setting and composition, plus integration with monad state, lens families provide some unique features:+description:        This package provides first class functional references in Van Laarhoven style supporting the following optics:                     .-                    * Polymorphic updating+                    * Lenses (view, over)                     .-                    * Traversals+                    * Traversals (toListOf, matching, over)                     .-                    * Cast projection functions to read-only lenses+                    * Setters (over)                     .-                    * Cast \"toList\" functions to read-only traversals+                    * Grates (zipWithOf, under, review)                     .-                    * Cast semantic editor combinators to modify-only traversals.+                    * Resetters (under)+                    .+                    * Adapters (view, review)+                    .+                    * Grids (toListOf, over / under, review)+                    .+                    * Prisms (matching, over / under, review)+                    .+                    * Getters (view)+                    .+                    * Folders (toListOf)+                    .+                    * Reviewers (review)  source-repository head   type:     darcs-  location: http://r6.ca/lens-family+  location: https://hub.darcs.net/roconnor/lens-family  library   extensions:       Rank2Types   build-depends:-    base                 >= 4.8     && < 5,+    base                 >= 4.11    && < 5,     containers           >= 0.5.8   && < 0.7,-    transformers         >= 0.2.0   && < 0.6,-    mtl                  >= 2.1     && < 2.3,-    lens-family-core     >= 1.2.2   && < 1.3+    transformers         >= 0.3.0   && < 0.6,+    mtl                  >= 2.2     && < 2.3,+    lens-family-core     >= 2.0.0   && < 2.1    exposed-modules:     Lens.Family2.Unchecked
src/Lens/Family2.hs view
@@ -1,6 +1,6 @@ {-# LANGUAGE Rank2Types #-} -- | This is the main module for end-users of lens-families.--- If you are not building your own lenses or traversals, but just using functional references made by others, this is the only module you need.+-- If you are not building your own optics such as lenses, traversals, grates, etc., but just using optics made by others, this is the only module you need. module Lens.Family2 ( -- * Lenses --@@ -24,7 +24,7 @@ -- @record & l1 .~ value1 & l2 .~ value2@ -- -- Lenses are implemented in van Laarhoven style.--- Lenses have type @'Functor' f => (b -> f b) -> a -> f a@ and lens families have type @'Functor' f => (b i -> f (b j)) -> a i -> f (a j)@.+-- Lenses have type @'Functor' f => (a -> f a) -> s -> f s@ and lens families have type @'Functor' f => (a i -> f (a j)) -> s i -> f (s j)@. -- -- Keep in mind that lenses and lens families can be used directly for functorial updates. -- For example, @_2 id@ gives you strength.@@ -35,13 +35,13 @@ -- -- > -- | 'sharedUpdate' returns the *identical* object if the update doesn't change anything. -- > -- This is useful for preserving sharing.--- > sharedUpdate :: Eq b => LensLike' Maybe a b -> (b -> b) -> a -> a--- > sharedUpdate l f a = fromMaybe a (l f' a)+-- > sharedUpdate :: Eq a => LensLike' Maybe s a -> (a -> a) -> s -> s+-- > sharedUpdate l f s = fromMaybe s (l f' s) -- >  where--- >   f' b | fb == b  = Nothing--- >        | otherwise = Just fb+-- >   f' a | b == a    = Nothing+-- >        | otherwise = Just b -- >    where--- >     fb = f b+-- >     b = f a  -- * Traversals --@@ -56,15 +56,78 @@ -- -- When 'LF..~' is used with a traversal, all referenced fields will be set to the same value, and when 'LF.%~' is used with a traversal, all referenced fields will be modified with the same function. ----- Like lenses, traversals can be composed with '.', and because every lens is automatically a traversal, lenses and traversals can be composed with '.' yielding a traversal.+-- A variant of '^?' call 'matching' returns 'Either' a 'Right' value which is the first value of the traversal, or a 'Left' value which is a "proof" that the traversal has no elements.+-- The "proof" consists of the original input structure, but in the case of polymorphic families, the type parameter is replaced with a fresh type variable, thus proving that the type parameter was unused. --+-- Like all optics, traversals can be composed with '.', and because every lens is automatically a traversal, lenses and traversals can be composed with '.' yielding a traversal.+-- -- Traversals are implemented in van Laarhoven style.--- Traversals have type @'Applicative' f => (b -> f b) -> a -> f a@ and traversal families have type @'Applicative' f => (b i -> f (b j)) -> a i -> f (a j)@.+-- Traversals have type @'Applicative' f => (a -> f a) -> s -> f s@ and traversal families have type @'Applicative' f => (a i -> f (a j)) -> s i -> f (s j)@. ----- For stock lenses and traversals, see "Lens.Family2.Stock".++-- * Grates ----- To build your own lenses and traversals, see "Lens.Family2.Unchecked".+-- | 'zipWithOf' can be used with grates to zip two structure together provided a binary operation. --+-- 'under' can be to modify each value in a structure according to a function.  This works analogous to how 'over' works for lenses and traversals.+--+-- 'LF.review' can be used with grates to construct a constant grate from a single value.  This is like a 0-ary @zipWith@ function.+--+-- 'degrating' can be used to build higher arity @zipWithOf@ functions:+--+-- > zipWith3Of :: AGrate s t a b -> (a -> a -> a -> b) -> s -> s -> s -> t+-- > zipWith3Of l f s1 s2 s3 = degrating l (\k -> f (k s1) (k s2) (k s3))+--+-- Like all optics, grates can be composed with '.', and 'id' is the identity grate.+--+-- Grates are implemented in van Laarhoven style.+--+-- Grates have type @'Functor' g => (g a -> a) -> g s -> s@ and grate families have type @'Functor' g => (g (a i) -> a j) -> g (s i) -> s j@.+--+-- Keep in mind that grates and grate families can be used directly for functorial zipping.  For example,+--+-- > both sum :: Num a => [(a, a)] -> (a, a)+--+-- will take a list of pairs return the sum of the first components and the sum of the second components.  For another example,+--+-- > cod id :: Functor f => f (r -> a) -> r -> f a+--+-- will turn a functor full of functions into a function returning a functor full of results.++-- * Adapters, Grids, and Prisms+--+-- | The Adapter, Prism, and Grid optics are all 'AdapterLike' optics and typically not used directly, but either converted to a 'LensLike' optic using 'under', or into a 'GrateLike' optic using 'over'.+-- See 'under' and 'over' for details about which conversions are possible.+--+-- These optics are implemented in van Laarhoven style.+--+-- * Adapters have type @('Functor' f, 'Functor' g) => (g a -> f a) -> g s -> f s@ and Adapters families have type @('Functor' f, 'Functor' g) => (g (a i) -> f (a j)) -> g (s i) -> f (s j)@.+--+-- * Grids have type @('Applicative' f, 'Functor' g) => (g a -> f a) -> g s -> f s@ and Grids families have type @('Applicative' f, 'Functor' g) => (g (a i) -> f (a j)) -> g (s i) -> f (s j)@.+--+-- * Prisms have type @('Applicative' f, 'Traversable' g) => (g a -> f a) -> g s -> f s@ and Prisms families have type @('Applicative' f, 'Traversable' g) => (g (a i) -> f (a j)) -> g (s i) -> f (s j)@.+--+-- Keep in mind that these optics and their families can sometimes be used directly, without using 'over' and 'under'.  Sometimes you can take advantage of the fact that+--+-- @+--    LensLike f (g s) t (g a) b+--   ==+--    AdapterLike f g s t a b+--   ==+--    GrateLike g s (f t) a (f b)+-- @+--+-- For example, if you have a grid for your structure to another type that has an @Arbitray@ instance, such as grid from a custom word type to 'Bool', e.g. @myWordBitVector :: (Applicative f, Functor g) => AdapterLike' f g MyWord Bool@, you can use the grid to create an @Arbitrary@ instance for your structure by directly applying 'LF.review':+--+-- > instance Arbitrary MyWord where+-- >   arbitrary = review myWordBitVector arbitrary++-- * Building and Finding Optics+--+-- | To build your own optics, see "Lens.Family2.Unchecked".+--+-- For stock optics, see "Lens.Family2.Stock".+-- -- References: -- -- * <http://www.twanvl.nl/blog/haskell/cps-functional-references>@@ -74,154 +137,211 @@ -- * <http://comonad.com/reader/2012/mirrored-lenses/> -- -- * <http://conal.net/blog/posts/semantic-editor-combinators>+--+-- * <https://r6research.livejournal.com/28050.html>  -- * Documentation     to, LF.view, (LF.^.)   , folding, LF.views, (^..), (^?)   , toListOf, allOf, anyOf, firstOf, lastOf, sumOf, productOf   , lengthOf, nullOf-  , LF.backwards+  , matching   , over, (%~), set, (.~)+  , LF.review, zipWithOf, degrating+  , under, reset   , (LF.&) -- * Pseudo-imperatives   , (+~), (*~), (-~), (//~), (&&~), (||~), (<>~) -- * Types+  , Adapter, Adapter'+  , Prism, Prism'   , Lens, Lens'   , Traversal, Traversal'   , Setter, Setter'   , Getter, Getter'   , Fold, Fold'+  , Grate, Grate'+  , Grid, Grid'+  , Reviewer, Reviewer'+  , LF.AdapterLike, LF.AdapterLike'   , LF.LensLike, LF.LensLike'+  , LF.GrateLike, LF.GrateLike'   , LF.FoldLike, LF.FoldLike'   , LF.Constant   , LF.Phantom   , Identical--- * Re-exports-  , Applicative, Foldable, Monoid-  , LF.Backwards   ) where -import Control.Applicative (Applicative)-import Data.Foldable (Foldable)-import Data.Monoid (Monoid) import qualified Lens.Family as LF-import Lens.Family2.Unchecked ( Lens, Lens'-                              , Traversal, Traversal'-                              , Setter, Setter', Identical-                              )+import Lens.Family2.Unchecked -type Fold a a' b b' = forall f. (LF.Phantom f, Applicative f) => LF.LensLike f a a' b b'-type Fold' a b = forall f. (LF.Phantom f, Applicative f) => LF.LensLike' f a b+type Grid s t a b = forall f g. (Applicative f, Functor g) => LF.AdapterLike f g s t a b+type Grid' s a = forall f g. (Applicative f, Functor g) => LF.AdapterLike' f g s a -type Getter a a' b b' = forall f. LF.Phantom f => LF.LensLike f a a' b b'-type Getter' a b = forall f. LF.Phantom f=> LF.LensLike' f a b+type Fold s t a b = forall f. (LF.Phantom f, Applicative f) => LF.LensLike f s t a b+type Fold' s a = forall f. (LF.Phantom f, Applicative f) => LF.LensLike' f s a +type Getter s t a b = forall f. LF.Phantom f => LF.LensLike f s t a b+type Getter' s a = forall f. LF.Phantom f=> LF.LensLike' f s a++type Reviewer s t a b = forall f. LF.Phantom f => LF.GrateLike f s t a b+type Reviewer' s a = forall f. LF.Phantom f => LF.GrateLike' f s a+ -- |'to' promotes a projection function to a read-only lens called a getter. -- To demote a lens to a projection function, use the section @(^.l)@ or @view l@. -- -- >>> (3 :+ 4, "example")^._1.to(abs) -- 5.0 :+ 0.0-to :: (a -> b) -> Getter a a' b b'+to :: (s -> a) -> Getter s t a b to = LF.to  -- | 'folding' promotes a \"toList\" function to a read-only traversal called a fold. -- -- To demote a traversal or fold to a \"toList\" function use the section @(^..l)@ or @toListOf l@.-folding :: Foldable f => (a -> f b) -> Fold a a' b b'+folding :: Foldable f => (s -> f a) -> Fold s t a b folding = LF.folding  -- | Returns a list of all of the referenced values in order.-toListOf :: Fold a a' b b' -> a -> [b]+toListOf :: Fold s t a b -> s -> [a] toListOf l = LF.toListOf l  -- | Returns true if all of the referenced values satisfy the given predicate.-allOf :: Fold a a' b b' -> (b -> Bool) -> a -> Bool+allOf :: Fold s t a b -> (a -> Bool) -> s -> Bool allOf l = LF.allOf l  -- | Returns true if any of the referenced values satisfy the given predicate.-anyOf :: Fold a a' b b' -> (b -> Bool) -> a -> Bool+anyOf :: Fold s t a b -> (a -> Bool) -> s -> Bool anyOf l = LF.anyOf l  -- | Returns 'Just' the first referenced value. -- Returns 'Nothing' if there are no referenced values. -- See '^?' for an infix version of 'firstOf'-firstOf :: Fold a a' b b' -> a -> Maybe b+firstOf :: Fold s t a b -> s -> Maybe a firstOf l = LF.firstOf l  -- | Returns 'Just' the last referenced value. -- Returns 'Nothing' if there are no referenced values.-lastOf :: Fold a a' b b' -> a -> Maybe b+lastOf :: Fold s t a b -> s -> Maybe a lastOf l = LF.lastOf l  -- | Returns the sum of all the referenced values.-sumOf :: Num b => Fold a a' b b' -> a -> b+sumOf :: Num a => Fold s t a b -> s -> a sumOf l = LF.sumOf l  -- | Returns the product of all the referenced values.-productOf :: Num b => Fold a a' b b' -> a -> b+productOf :: Num a => Fold s t a b -> s -> a productOf l = LF.productOf l  -- | Counts the number of references in a traversal or fold for the input.-lengthOf :: Num r => Fold a a' b b' -> a -> r+lengthOf :: Num r => Fold s t a b -> s -> r lengthOf l = LF.lengthOf l  -- | Returns true if the number of references in the input is zero.-nullOf :: Fold a a' b b' -> a -> Bool+nullOf :: Fold s t a b -> s -> Bool nullOf l = LF.nullOf l  infixl 8 ^..  -- | Returns a list of all of the referenced values in order.-(^..) :: a -> Fold a a' b b' -> [b]+(^..) :: s -> Fold s t a b -> [a] x^..l = x LF.^.. l  infixl 8 ^?  -- | Returns 'Just' the first referenced value. -- Returns 'Nothing' if there are no referenced values.-(^?) :: a -> Fold a a' b b' -> Maybe b+(^?) :: s -> Fold s t a b -> Maybe a x^?l = x LF.^? l +-- | Returns 'Right' of the first referenced value.+-- Returns 'Left' the original value when there are no referenced values.+-- In case there are no referenced values, the result might have a fresh type parameter, thereby proving the original value had no referenced values.+matching :: Traversal s t a b -> s -> Either t a+matching l = LF.matching l++zipWithOf :: Grate s t a b -> (a -> a -> b) -> s -> s -> t+-- ^ Returns a binary instance of a grate.+--+-- @+-- zipWithOf l f x y = degrating l (\k -> f (k x) (k y))+-- @+zipWithOf l = LF.zipWithOf l++degrating :: Grate s t a b -> ((s -> a) -> b) -> t+-- ^ Demote a grate to its normal, higher-order function, form.+--+-- @+-- degrating . grate = id+-- grate . degrating = id+-- @+degrating l = LF.degrating l++-- | Demote a resetter to a semantic editor combinator.+--+-- @+-- under :: Prism s t a b -> Traversal s t a b+-- under :: Grid s t a b -> Traversal s t a b+-- under :: Adapter s t a b -> Lens s t a b+-- @+--+-- Covert an 'AdapterLike' optic into a 'LensLike' optic.+--+-- Note: this function is unrelated to the lens package's @under@ function.+under :: Resetter s t a b -> (a -> b) -> s -> t+under l = LF.under l++-- | Set all referenced fields to the given value.+reset :: Resetter s t a b -> b -> s -> t+reset l = LF.reset l+ -- | Demote a setter to a semantic editor combinator.-over :: Setter a a' b b' -> (b -> b') -> a -> a'+--+-- @+-- over :: Prism s t a b -> Reviwer s t a b+-- over :: Grid s t a b -> Grate s t a b+-- over :: Adapter s t a b -> Grate s t a b+-- @+--+-- Covert an 'AdapterLike' optic into a 'GrateLike' optic.+over :: Setter s t a b -> (a -> b) -> s -> t over l = LF.over l  infixr 4 %~  -- | Modify all referenced fields.-(%~) :: Setter a a' b b' -> (b -> b') -> a -> a'+(%~) :: Setter s t a b -> (a -> b) -> s -> t l %~ f = l LF.%~ f  infixr 4 .~  -- | Set all referenced fields to the given value.-(.~) :: Setter a a' b b' -> b' -> a -> a'+(.~) :: Setter s t a b -> b -> s -> t l .~ b = l LF..~ b  -- | Set all referenced fields to the given value.-set :: Setter a a' b b' -> b' -> a -> a'+set :: Setter s t a b -> b -> s -> t set l = LF.set l  infixr 4 +~, -~, *~ -(+~), (-~), (*~) :: Num b => Setter' a b -> b -> a -> a-f +~ b = f LF.+~ b-f -~ b = f LF.-~ b-f *~ b = f LF.*~ b+(+~), (-~), (*~) :: Num a => Setter s t a a -> a -> s -> t+l +~ a = l LF.+~ a+l -~ a = l LF.-~ a+l *~ a = l LF.*~ a  infixr 4 //~ -(//~) :: Fractional b => Setter' a b -> b -> a -> a-f //~ b = f LF.//~ b+(//~) :: Fractional a => Setter s t a a -> a -> s -> t+l //~ a = l LF.//~ a  infixr 4 &&~, ||~ -(&&~), (||~) :: Setter' a Bool -> Bool -> a -> a-f &&~ b = f LF.&&~ b-f ||~ b = f LF.||~ b+(&&~), (||~) :: Setter s t Bool Bool -> Bool -> s -> t+l &&~ a = l LF.&&~ a+l ||~ a = l LF.||~ a  infixr 4 <>~  -- | Monoidally append a value to all referenced fields.-(<>~) :: (Monoid o) => Setter' a o -> o -> a -> a-f <>~ o = f LF.<>~ o+(<>~) :: (Monoid a) => Setter s t a a -> a -> s -> t+l <>~ a = l LF.<>~ a
src/Lens/Family2/State/Lazy.hs view
@@ -27,47 +27,41 @@   , FoldLike, Constant   , Setter, Setter', Identical   , LFS.StateT, MonadState, Writer-  , Monoid   ) where -import Data.Monoid (Monoid, mappend) import Data.Tuple (swap) import Control.Monad (liftM) import Control.Monad.Trans.Writer.Lazy (Writer, writer, runWriter) import Control.Monad.State.Lazy (MonadState, get, modify, modify', state)-import Lens.Family2 ( LensLike, LensLike'-                    , FoldLike, Constant-                    , Setter, Setter', Identical-                    , view, views, (%~)-                    )+import Lens.Family2 import qualified Lens.Family.State.Lazy as LFS -use :: MonadState a m => FoldLike b a a' b b' -> m b+use :: MonadState s m => FoldLike a s t a b -> m a -- ^ @--- use :: MonadState a m => Getter a a' b b' -> m b+-- use :: MonadState s m => Getter s t a b -> m a -- @ -- -- Retrieve a field of the state -- -- @--- use :: (Monoid b, MonadState a m) => Fold a a' b b' -> m b+-- use :: (MonadState s m, Monoid a) => Fold s t a b -> m a -- @ -- -- Retrieve a monoidal summary of all the referenced fields from the state use l = view l `liftM` get -uses :: MonadState a m => FoldLike r a a' b b' -> (b -> r) -> m r+uses :: MonadState s m => FoldLike r s t a b -> (a -> r) -> m r -- ^ @--- uses :: (MonadState a m, Monoid r) => Fold a a' b b' -> (b -> r) -> m r+-- uses :: (MonadState s m, Monoid r) => Fold s t a b -> (a -> r) -> m r -- @ ----- Retrieve all the referenced fields from the state and foldMap the results together with @f :: b -> r@.+-- Retrieve all the referenced fields from the state and foldMap the results together with @f :: a -> r@. -- -- @--- uses :: MonadState a m => Getter a a' b b' -> (b -> r) -> m r+-- uses :: MonadState s m => Getter s t a b -> (a -> r) -> m r -- @ ----- Retrieve a field of the state and pass it through the function @f :: b -> r@.+-- Retrieve a field of the state and pass it through the function @f :: a -> r@. -- -- @uses l f = f \<$> use l@ uses l f = views l f `liftM` get@@ -75,36 +69,36 @@ infix 4 %=  -- | Modify a field of the state.-(%=) :: MonadState a m => Setter a a b b' -> (b -> b') -> m ()+(%=) :: MonadState s m => Setter s s a b -> (a -> b) -> m () l %= f = modify (l %~ f)  infix 4 .=  -- | Set a field of the state.-(.=) :: MonadState a m => Setter a a b b' -> b' -> m ()+(.=) :: MonadState s m => Setter s s a b -> b -> m () l .= v = l %= const v  -- | Set a field of the state.-assign :: MonadState a m => Setter a a b b' -> b' -> m ()+assign :: MonadState s m => Setter s s a b -> b -> m () assign = (.=)  infixr 2 <~  -- | Set a field of the state using the result of executing a stateful command.-(<~) :: MonadState a m => Setter a a b b' -> m b' -> m ()+(<~) :: MonadState s m => Setter s s a b -> m b -> m () l <~ v = assign l =<< v  infix 4 %%= -(%%=) :: MonadState a m => LensLike (Writer c) a a b b' -> (b -> (c, b')) -> m c+(%%=) :: MonadState s m => LensLike (Writer c) s s a b -> (a -> (c, b)) -> m c -- ^ @--- (%%=) :: MonadState a m => Lens a a b b' -> (b -> (c, b')) -> m c+-- (%%=) :: MonadState s m => Lens s s a b -> (a -> (c, b)) -> m c -- @ -- -- Modify a field of the state while returning another value. -- -- @--- (%%=) :: (MonadState a m, Monoid c) => Traversal a a b b' -> (b -> (c, b')) -> m c+-- (%%=) :: (MonadState s m, Monoid c) => Traversal s s a b -> (a -> (c, b)) -> m c -- @ -- -- Modify each field of the state and return the 'mconcat' of the other values.@@ -112,53 +106,53 @@  infixr 4 +=, -=, *= -(+=), (-=), (*=) :: (MonadState a m, Num b) => Setter' a b -> b -> m ()-f += b = f %= (+ b)-f -= b = f %= subtract b-f *= b = f %= (* b)+(+=), (-=), (*=) :: (MonadState s m, Num a) => Setter' s a -> a -> m ()+l += a = l %= (+ a)+l -= a = l %= subtract a+l *= a = l %= (* a)  infixr 4 //= -(//=) :: (MonadState a m, Fractional b) => Setter' a b -> b -> m ()-f //= b = f %= (/ b)+(//=) :: (MonadState s m, Fractional a) => Setter' s a -> a -> m ()+l //= a = l %= (/ a)  infixr 4 &&=, ||= -(&&=), (||=) :: MonadState a m => Setter' a Bool -> Bool -> m ()-f &&= b = f %= (&& b)-f ||= b = f %= (|| b)+(&&=), (||=) :: MonadState s m => Setter' s Bool -> Bool -> m ()+l &&= a = l %= (&& a)+l ||= a = l %= (|| a)  infixr 4 <>=  -- | Monoidally append a value to all referenced fields of the state.-(<>=) :: (Monoid o, MonadState a m) => Setter' a o -> o -> m ()-f <>= b = f %= (`mappend` b)+(<>=) :: (MonadState s m, Monoid a) => Setter' s a -> a -> m ()+l <>= a = l %= (<> a)  infix 4 %!=  -- | Strictly modify a field of the state.-(%!=) :: MonadState a m => Setter a a b b' -> (b -> b') -> m ()+(%!=) :: MonadState s m => Setter s s a b -> (a -> b) -> m () l %!= f = modify' (l %~ f)  infixr 4 +!=, -!=, *!= -(+!=), (-!=), (*!=) :: (MonadState a m, Num b) => Setter' a b -> b -> m ()-f +!= b = f %!= (+ b)-f -!= b = f %!= subtract b-f *!= b = f %!= (* b)+(+!=), (-!=), (*!=) :: (MonadState s m, Num a) => Setter' s a -> a -> m ()+l +!= a = l %!= (+ a)+l -!= a = l %!= subtract a+l *!= a = l %!= (* a)  infixr 4 //!= -(//!=) :: (MonadState a m, Fractional b) => Setter' a b -> b -> m ()-f //!= b = f %!= (/ b)+(//!=) :: (MonadState s m, Fractional a) => Setter' s a -> a -> m ()+l //!= a = l %!= (/ a)  infixr 4 &&!=, ||!= -(&&!=), (||!=) :: MonadState a m => Setter' a Bool -> Bool -> m ()-f &&!= b = f %!= (&& b)-f ||!= b = f %!= (|| b)+(&&!=), (||!=) :: MonadState s m => Setter' s Bool -> Bool -> m ()+l &&!= a = l %!= (&& a)+l ||!= a = l %!= (|| a)  infixr 4 <>!= -(<>!=) :: (Monoid o, MonadState a m) => Setter' a o -> o -> m ()-f <>!= b = f %!= (`mappend` b)+(<>!=) :: (MonadState s m, Monoid a) => Setter' s a -> a -> m ()+l <>!= a = l %!= (<> a)
src/Lens/Family2/State/Strict.hs view
@@ -27,47 +27,41 @@   , FoldLike, Constant   , Setter, Setter', Identical   , LFS.StateT, MonadState, Writer-  , Monoid   ) where -import Data.Monoid (Monoid, mappend) import Data.Tuple (swap) import Control.Monad (liftM) import Control.Monad.Trans.Writer.Lazy (Writer, writer, runWriter) import Control.Monad.State.Strict (MonadState, get, modify, modify', state)-import Lens.Family2 ( LensLike, LensLike'-                    , FoldLike, Constant-                    , Setter, Setter', Identical-                    , view, views, (%~)-                    )+import Lens.Family2 import qualified Lens.Family.State.Strict as LFS -use :: MonadState a m => FoldLike b a a' b b' -> m b+use :: MonadState s m => FoldLike a s t a b -> m a -- ^ @--- use :: MonadState a m => Getter a a' b b' -> m b+-- use :: MonadState s m => Getter s t a b -> m a -- @ -- -- Retrieve a field of the state -- -- @--- use :: (Monoid b, MonadState a m) => Fold a a' b b' -> m b+-- use :: (MonadState s m, Monoid a) => Fold s t a b -> m a -- @ -- -- Retrieve a monoidal summary of all the referenced fields from the state use l = view l `liftM` get -uses :: MonadState a m => FoldLike r a a' b b' -> (b -> r) -> m r+uses :: MonadState s m => FoldLike r s t a b -> (a -> r) -> m r -- ^ @--- uses :: (MonadState a m, Monoid r) => Fold a a' b b' -> (b -> r) -> m r+-- uses :: (MonadState s m, Monoid r) => Fold s t a b -> (a -> r) -> m r -- @ ----- Retrieve all the referenced fields from the state and foldMap the results together with @f :: b -> r@.+-- Retrieve all the referenced fields from the state and foldMap the results together with @f :: a -> r@. -- -- @--- uses :: MonadState a m => Getter a a' b b' -> (b -> r) -> m r+-- uses :: MonadState s m => Getter s t a b -> (a -> r) -> m r -- @ ----- Retrieve a field of the state and pass it through the function @f :: b -> r@.+-- Retrieve a field of the state and pass it through the function @f :: a -> r@. -- -- @uses l f = f \<$> use l@ uses l f = views l f `liftM` get@@ -75,36 +69,36 @@ infix 4 %=  -- | Modify a field of the state.-(%=) :: MonadState a m => Setter a a b b' -> (b -> b') -> m ()+(%=) :: MonadState s m => Setter s s a b -> (a -> b) -> m () l %= f = modify (l %~ f)  infix 4 .=  -- | Set a field of the state.-(.=) :: MonadState a m => Setter a a b b' -> b' -> m ()+(.=) :: MonadState s m => Setter s s a b -> b -> m () l .= v = l %= const v  -- | Set a field of the state.-assign :: MonadState a m => Setter a a b b' -> b' -> m ()+assign :: MonadState s m => Setter s s a b -> b -> m () assign = (.=)  infixr 2 <~  -- | Set a field of the state using the result of executing a stateful command.-(<~) :: MonadState a m => Setter a a b b' -> m b' -> m ()+(<~) :: MonadState s m => Setter s s a b -> m b -> m () l <~ v = assign l =<< v  infix 4 %%= -(%%=) :: MonadState a m => LensLike (Writer c) a a b b' -> (b -> (c, b')) -> m c+(%%=) :: MonadState s m => LensLike (Writer c) s s a b -> (a -> (c, b)) -> m c -- ^ @--- (%%=) :: MonadState a m => Lens a a b b' -> (b -> (c, b')) -> m c+-- (%%=) :: MonadState s m => Lens s s a b -> (a -> (c, b)) -> m c -- @ -- -- Modify a field of the state while returning another value. -- -- @--- (%%=) :: (MonadState a m, Monoid c) => Traversal a a b b' -> (b -> (c, b')) -> m c+-- (%%=) :: (MonadState s m, Monoid c) => Traversal s s a b -> (a -> (c, b)) -> m c -- @ -- -- Modify each field of the state and return the 'mconcat' of the other values.@@ -112,53 +106,53 @@  infixr 4 +=, -=, *= -(+=), (-=), (*=) :: (MonadState a m, Num b) => Setter' a b -> b -> m ()-f += b = f %= (+ b)-f -= b = f %= subtract b-f *= b = f %= (* b)+(+=), (-=), (*=) :: (MonadState s m, Num a) => Setter' s a -> a -> m ()+l += a = l %= (+ a)+l -= a = l %= subtract a+l *= a = l %= (* a)  infixr 4 //= -(//=) :: (MonadState a m, Fractional b) => Setter' a b -> b -> m ()-f //= b = f %= (/ b)+(//=) :: (MonadState s m, Fractional a) => Setter' s a -> a -> m ()+l //= a = l %= (/ a)  infixr 4 &&=, ||= -(&&=), (||=) :: MonadState a m => Setter' a Bool -> Bool -> m ()-f &&= b = f %= (&& b)-f ||= b = f %= (|| b)+(&&=), (||=) :: MonadState s m => Setter' s Bool -> Bool -> m ()+l &&= a = l %= (&& a)+l ||= a = l %= (|| a)  infixr 4 <>=  -- | Monoidally append a value to all referenced fields of the state.-(<>=) :: (Monoid o, MonadState a m) => Setter' a o -> o -> m ()-f <>= b = f %= (`mappend` b)+(<>=) :: (MonadState s m, Monoid a) => Setter' s a -> a -> m ()+l <>= a = l %= (<> a)  infix 4 %!=  -- | Strictly modify a field of the state.-(%!=) :: MonadState a m => Setter a a b b' -> (b -> b') -> m ()+(%!=) :: MonadState s m => Setter s s a b -> (a -> b) -> m () l %!= f = modify' (l %~ f)  infixr 4 +!=, -!=, *!= -(+!=), (-!=), (*!=) :: (MonadState a m, Num b) => Setter' a b -> b -> m ()-f +!= b = f %!= (+ b)-f -!= b = f %!= subtract b-f *!= b = f %!= (* b)+(+!=), (-!=), (*!=) :: (MonadState s m, Num a) => Setter' s a -> a -> m ()+l +!= a = l %!= (+ a)+l -!= a = l %!= subtract a+l *!= a = l %!= (* a)  infixr 4 //!= -(//!=) :: (MonadState a m, Fractional b) => Setter' a b -> b -> m ()-f //!= b = f %!= (/ b)+(//!=) :: (MonadState s m, Fractional a) => Setter' s a -> a -> m ()+l //!= a = l %!= (/ a)  infixr 4 &&!=, ||!= -(&&!=), (||!=) :: MonadState a m => Setter' a Bool -> Bool -> m ()-f &&!= b = f %!= (&& b)-f ||!= b = f %!= (|| b)+(&&!=), (||!=) :: MonadState s m => Setter' s Bool -> Bool -> m ()+l &&!= a = l %!= (&& a)+l ||!= a = l %!= (|| a)  infixr 4 <>!= -(<>!=) :: (Monoid o, MonadState a m) => Setter' a o -> o -> m ()-f <>!= b = f %!= (`mappend` b)+(<>!=) :: (MonadState s m, Monoid a) => Setter' s a -> a -> m ()+l <>!= a = l %!= (<> a)
src/Lens/Family2/Stock.hs view
@@ -1,51 +1,68 @@ {-# LANGUAGE Rank2Types #-}--- | This module contains lenses and traversals for common structures in Haskell.--- It also contains the combinators for lenses and traversals.+-- | This module contains lenses, prisms, grids, grates and traversals for common structures in Haskell.+-- It also contains the combinators for various kinds of optics.+--+-- A Function name with @'@ is a grate variant of a grid, and a function name with @_@ is a traversal variants of a grid or prism.+-- For example, 'both'' is the grate variant of 'both' while 'both_' is the traversal variant. module Lens.Family2.Stock (--- * Lens Combinators-    Stock.choosing-  , Stock.alongside-  , Stock.beside -- * Stock Lenses-  , _1, _2+    _1, _2   , chosen   , ix   , at, intAt   , at', intAt'   , contains, intContains--- * Stock Traversals+-- * Stock Prisms+  , lft, rgt+  , some, none+-- * Stock Grids   , both-  , _Left, _Right-  , _Just, _Nothing+  , bend, lend+-- * Stock Grates+  , cod+  , both'+  , bend', lend'+-- * Stock Traversals+  , both_+  , bend_, lend_+  , lft_, rgt_+  , some_, none_   , ignored -- * Stock SECs   , mapped+-- * Lens Combinators+  , Stock.alongside+  , Stock.backwards+  , Stock.beside, Stock.beside', Stock.beside_+  , Stock.choosing+  , Stock.from -- * Types   , Stock.AlongsideLeft, Stock.AlongsideRight+  , Stock.FromF, Stock.FromG -- * Re-exports   , Lens, Lens'+  , Grate, Grate'   , Traversal, Traversal'   , Setter+  , Stock.AdapterLike, Stock.AdapterLike'   , Stock.LensLike, Stock.LensLike'-  , Stock.Applicative, Stock.Identical+  , Stock.Identical, Stock.Backwards+  , Stock.FiniteBits   ) where -import qualified Lens.Family.Stock as Stock-import Lens.Family2 ( Lens, Lens'-                    , Traversal, Traversal'-                    , Setter-                    ) import qualified Data.Map as Map-import qualified Data.IntMap as IntMap import qualified Data.Set as Set+import qualified Data.IntMap as IntMap import qualified Data.IntSet as IntSet+import qualified Lens.Family.Stock as Stock+import Lens.Family2  -- | Lens on the first element of a pair.-_1 :: Lens (a, b) (a', b) a a'+_1 :: Lens (a, r) (b, r) a b _1 = Stock._1  -- | Lens on the second element of a pair.-_2 :: Lens (a, b) (a, b') b b'+_2 :: Lens (r, a) (r, b) a b _2 = Stock._2  -- | Lens on the Left or Right element of an ('Either' a a).@@ -80,25 +97,90 @@ intContains :: Int -> Lens' IntSet.IntSet Bool intContains = Stock.intContains +-- | A grate accessing the codomain of a function.+cod :: Grate (r -> a) (r -> b) a b+cod = Stock.cod++-- | A prism on the 'Left' element of an 'Either'.+lft :: Prism (Either a r) (Either b r) a b+lft = Stock.lft+ -- | Traversal on the 'Left' element of an 'Either'.-_Left :: Traversal (Either a b) (Either a' b) a a'-_Left = Stock._Left+lft_ :: Traversal (Either a r) (Either b r) a b+lft_ = Stock.lft_ +-- | A prism on the 'Right' element of an 'Either'.+rgt :: Prism (Either r a) (Either r b) a b+rgt = Stock.rgt+ -- | Traversal on the 'Right' element of an 'Either'.-_Right :: Traversal (Either a b) (Either a b') b b'-_Right = Stock._Right+rgt_ :: Traversal (Either r a) (Either r b) a b+rgt_ = Stock.rgt_ ++-- | A prism on the 'Just' element of a 'Maybe'.+some :: Prism (Maybe a) (Maybe b) a b+some = Stock.some+ -- | Traversal on the 'Just' element of a 'Maybe'.-_Just :: Traversal (Maybe a) (Maybe a') a a'-_Just = Stock._Just+some_ :: Traversal (Maybe a) (Maybe b) a b+some_ = Stock.some_ +-- | A prism on the 'Nothing' element of a 'Maybe'.+none :: Prism' (Maybe a) ()+none = Stock.none+ -- | Traversal on the 'Nothing' element of a 'Maybe'.-_Nothing :: Traversal' (Maybe a) ()-_Nothing = Stock._Nothing+none_ :: Traversal' (Maybe a) ()+none_ = Stock.none_ --- | Traversals on both elements of a pair @(a,a)@.-both :: Traversal (a,a) (b,b) a b+-- | A grid on both elements of a pair @(a,a)@.+both :: Grid (a,a) (b,b) a b both = Stock.both++-- | A grate on both elements of a pair @(a,a)@.+both' :: Grate (a,a) (b,b) a b+both' = Stock.both'++-- | Traversals on both elements of a pair @(a,a)@.+both_ :: Traversal (a,a) (b,b) a b+both_ = Stock.both_++-- | A grid from the least significant bit to the most significant bit of a 'FiniteBits' type.+--+-- Little endian order.+lend :: Stock.FiniteBits b => Grid' b Bool+lend = Stock.lend++-- | A grate from the least significant bit to the most significant bit of a 'FiniteBits' type.+--+-- Little endian order.+lend' :: Stock.FiniteBits b => Grate' b Bool+lend' = Stock.lend'++-- | A traversal from the least significant bit to the most significant bit of a 'FiniteBits' type.+--+-- Little endian order.+lend_ :: Stock.FiniteBits b => Traversal' b Bool+lend_ = Stock.lend_++-- | A grid from the most significant bit to the least significant bit of a 'FiniteBits' type.+--+-- Big endian order.+bend :: Stock.FiniteBits b => Grid' b Bool+bend = Stock.bend++-- | A grate from the most significant bit to the least significant bit of a 'FiniteBits' type.+--+-- Big endian order.+bend' :: Stock.FiniteBits b => Grate' b Bool+bend' = Stock.bend'++-- | A traversal from the most significant bit to the least significant bit of a 'FiniteBits' type.+--+-- Big endian order.+bend_ :: Stock.FiniteBits b => Traversal' b Bool+bend_ = Stock.bend_  -- | The empty traveral on any type. ignored :: Traversal a a b b'
src/Lens/Family2/Unchecked.hs view
@@ -1,30 +1,45 @@ {-# LANGUAGE Rank2Types #-} -- | /Caution/: Improper use of this module can lead to unexpected behaviour if the preconditions of the functions are not met. module Lens.Family2.Unchecked (+-- * Adapters+-- | An adapter represents a isomorphism between two types or a parametric isomorphism between two families of types.+-- For example we can build an adapter between the type families @'Either' a a@ and @('Bool', a)@ as follows:+--+-- > timesTwo :: Adapter (Either a a) (Either b b) (Bool, a) (Bool b)+-- > timesTwo f x = fmap yang . f . fmap yin+-- >  where+-- >   yin (True, a) = Left a+-- >   yin (False, a) = Right a+-- >   yang (Left a) = (True, a)+-- >   yang (Right a) = (False, a)+--+-- /Note/: It is possible to adapters without even depending on @lens-family@ by expanding away the type synonym.+--+-- > timesTwo :: (Functor f, Functor g) => (g (Either a a) -> f (Either b b)) -> g (Bool, a) -> f (Bool, b)+--+-- The function 'adapter' can also be used to construct adapters from a pair of mutually inverse functions.+ -- * Lenses--- | A lens family is created by separating a substructure from the rest of its structure by a functor.+-- | A lens focuses on a field of record type.+-- Lenses can be used to get and/or set the focused field. -- How to create a lens family is best illustrated by the common example of a field of a record: ----- > data MyRecord a = MyRecord { _myA :: a, _myB :: Int }+-- > data MyRecord a = MyRecord { _myA :: a, _myInt :: Int } -- >--- > -- The use of type variables a and a' allow for polymorphic updates.--- > myA :: Lens (MyRecord a) (MyRecord a') a a'--- > myA f (MyRecord a b) = (\a' -> MyRecord a' b) `fmap` (f a)+-- > -- The use of type variables a and b allow for polymorphic updates.+-- > myA :: Lens (MyRecord a) (MyRecord b) a b+-- > myA f (MyRecord a i) = (\b -> MyRecord b i) <$> f a -- >--- > -- The field _myB is monomorphic, so we can use a 'Lens'' type.+-- > -- The field _myInt is monomorphic, so we can use a 'Lens'' type. -- > -- However, the structure of the function is exactly the same as for Lens.--- > myB :: Lens' (MyRecord a) Int--- > myB f (MyRecord a b) = (\b' -> MyRecord a b') `fmap` (f b)+-- > myInt :: Lens' (MyRecord a) Int+-- > myInt f (MyRecord a i) = (\i' -> MyRecord a i') <$> f i ----- By following this template you can safely build your own lenses.--- To use this template, you do not need anything from this module other than the type synonyms 'Lens' and 'Lens'', and even they are optional.--- See the @lens-family-th@ package to generate this code using Template Haskell.+-- See the @lens-family-th@ package to generate this sort of code using Template Haskell. -- -- /Note/: It is possible to build lenses without even depending on @lens-family@ by expanding away the type synonym. ----- > -- A lens definition that only requires the Haskell "Prelude".--- > myA :: Functor f => (a -> f a') -> (MyRecord a) -> f (MyRecord a')--- > myA f (MyRecord a b) = (\a' -> MyRecord a' b) `fmap` (f a)+-- > myA :: Functor f => (a -> f b) -> (MyRecord a) -> f (MyRecord b) -- -- You can build lenses for more than just fields of records. -- Any value @l :: Lens a a' b b'@ is well-defined when it satisfies the two van Laarhoven lens laws:@@ -33,40 +48,38 @@ -- -- * @l (Compose . fmap f . g) === Compose . fmap (l f) . (l g)@ ----- The functions 'lens' and 'iso' can also be used to construct lenses.+-- The function 'lens' can also be used to construct lenses. -- The resulting lenses will be well-defined so long as their preconditions are satisfied.  -- * Traversals--- -- | If you have zero or more fields of the same type of a record, a traversal can be used to refer to all of them in order. -- Multiple references are made by replacing the 'Functor' constraint of lenses with an 'Control.Applicative.Applicative' constraint. -- Consider the following example of a record with two 'Int' fields. ----- > data MyRecord = MyRecord { _myA :: Int, _myB :: Int }+-- > data MyRecord = MyRecord { _myA :: Int, _myB :: Int, _myC :: Bool } -- > -- > -- myInts is a traversal over both fields of MyRecord. -- > myInts :: Traversal' MyRecord Int--- > myInts f (MyRecord a b) = MyRecord <$> f a <*> f b+-- > myInts f (MyRecord a b c) = MyRecord <$> f a <*> f b <*> pure c ----- If the record and the referenced fields are parametric, you can can build traversals with polymorphic updating.+-- If the record and the referenced fields are parametric, you can can build polymrphic traversals. -- Consider the following example of a record with two 'Maybe' fields. ----- > data MyRecord a = MyRecord { _myA :: Maybe a, _myB :: Maybe a }+-- > data MyRecord a = MyRecord { _myA0 :: Maybe a, _myA1 :: Maybe a, myC :: Bool } -- >--- > -- myInts is a traversal over both fields of MyRecord.--- > myMaybes :: Traversal (MyRecord a) (MyRecord a') (Maybe a) (Maybe a')--- > myMaybes f (MyRecord a b) = MyRecord <$> f a <*> f b+-- > -- myMaybes is a traversal over both fields of MyRecord.+-- > myMaybes :: Traversal (MyRecord a) (MyRecord b) (Maybe a) (Maybe b)+-- > myMaybes f (MyRecord a0 a1 c) = MyRecord <$> f a0 <*> f a1 <*> pure c ----- /Note/: As with lenses, is possible to build traversals without even depending on @lens-family-core@ by expanding away the type synonym.+-- /Note/: It is possible to build traversals without even depending on @lens-family@ by expanding away the type synonym. ----- > -- A traversal definition that only requires the Haskell "Prelude".--- > myMaybes :: Applicative f => (Maybe a -> f (Maybe a')) -> MyRecord a -> f (MyRecord a')--- > myMaybes f (MyRecord a b) = MyRecord <$> f a <*> f b+-- > myMaybes :: Applicative f => (Maybe a -> f (Maybe b)) -> MyRecord a -> f (MyRecord b)+-- > myMaybes f (MyRecord a0 a1 c) = MyRecord <$> f a0 <*> f a1 <*> pure c ----- Unfortuantely, there are no helper functions for making traversals.--- You must make them by hand.+-- Unfortunately, there are no helper functions for making traversals.+-- In most cases, you must make them by hand. ----- Any value @t :: Traversal a a' b b'@ is well-defined when it satisfies the two van Laarhoven traversal laws:+-- Any value @t :: Traversal s t a b@ is well-defined when it satisfies the two van Laarhoven traversal laws: -- -- * @t Identity === Identity@ --@@ -74,69 +87,227 @@ -- -- 'Data.Traversable.traverse' is the canonical traversal for various containers. +-- * Prisms+-- | A prism focuses on a single variant of a type.+-- They can be used to 'Lens.Family2.matching' / 'Lens.Family2.review' the focused variant.+-- Consider the following example.+--+-- > data MySum a = MyA a | MyB Int+-- >+-- > -- myA is a prism for the MyA variant of MySum+-- > myA :: Prism (MySum a) (MySum b) a b+-- > myA f = either pure (fmap MyA . f) . traverse h+-- >  where+-- >   h (MyA a) = Right a+-- >   h (MyB n) = Left (MyB n)+--+-- This prism can be used with 'Lens.Family2.matching' via 'Lens.Family2.under':+--+-- @ 'Lens.Family2.matching' ('Lens.Family2.under' myA) :: MySum a -> Either (MySum b) a @+--+-- This prism can be used with 'Lens.Family2.review' via 'Lens.Family2.over':+--+-- @ 'Lens.Family2.review' ('Lens.Family2.over' myA) :: a -> MySum a @+--+-- /Note/: It is possible to build prisms without even depending on @lens-family@ by expanding away the type synonym.+--+-- > myA :: (Appicative f, Traversable g) => (g a -> f b) -> g (MySum a) -> f (MySum b)+--+-- You can build prism for more than just constructors of sum types.+-- Any value @p :: Prism s t a b@ is well-defined when it satisfies the prism laws:+--+-- * @matching (under p) (review (over p) b) === Right b@+--+-- * @(id ||| review (over p)) (matching (under p) s) === s@+--+-- * @left (match (under p)) (matching (under p) s) === left Left (matching (under p) s)@+--+-- The function 'prism' can also be used to construct prisms.+-- The resulting prisms will be well-defined so long as their preconditions are satisfied.++-- * Grates+-- | A grate focuses on the contents of a representable functor.+-- In other words, a grate focuses on the codomain of a function type or something isomorphic to a function type.+-- They are used to lift operations on this codomain to operations on the larger structure via zipping.+-- Consider the following example of a stream of 'Int's.+--+-- > data IntStream = IntStream { hd :: Int, tl :: IntStream }+-- >+-- > -- myInts is a grate over the Ints of IntStream.+-- > myInts :: Grate g IntStream Int+-- > myInts f s = IntStream (f (hd <$> s)) (myInts f (tl <$> s))+--+-- If the contents are parametric, you can can build polymorphic grates.+-- Consider the following example of a generic stream.+--+-- > data Stream a = Stream { hd :: a, tl :: Stream a }+-- >+-- > -- myStream is a grate over the contents of a Stream.+-- > myStream :: Grate (Stream a) (Stream b) a b+-- > myStream f s = Stream (f (hd <$> s)) (myStream f (tl <$> s))+--+-- /Note/: It is possible to build grates without even depending on @lens-family@ by expanding away the type synonym.+--+-- > myStream :: Functor g => (g (Stream a) -> Stream b) -> g a -> b+--+-- Any value @t :: Grate s t a b@ is a well-defined grate when it satisfies the two van Laarhoven traversal laws:+--+-- * @t runIdentity === runIdentity@+--+-- * @t (f . fmap g . runCompose) === (t f) . fmap (t g) . runCompose@+--+-- The function 'grate' can also be used to construct grates from graters.+-- The resulting grates will be well-defined so long as the preconditions are satisfied.++-- * Grids+-- | A grid is both a traversal and a grate.+-- When you have a type that is isomorphic to a fixed and finite number of copies of another type, a grid can be used to zip or traverse them.+-- Consider the following example of a record with exactly two 'Int' fields.+--+-- > data MyRecord = MyRecord { _myA :: Int, _myB :: Int }+-- >+-- > -- myInts is a grid over both fields of MyRecord.+-- > myInts :: Grid f g MyRecord Int+-- > myInts f r = MyRecord <$> f (_myA <$> r) <*> f (_myB <$> r)+--+-- If the record and the referenced fields are parametric, you can can build polymorphic grids.+-- Consider the following example of a record with exactly two 'Maybe' fields.+--+-- > data MyRecord a = MyRecord { _myA0 :: Maybe a, _myA1 :: Maybe a }+-- >+-- > -- myMaybes is a traversal over both fields of MyRecord.+-- > myMaybes :: Grid (MyRecord a) (MyRecord b) (Maybe a) (Maybe b)+-- > myMaybes f r = MyRecord <$> f (_myA0 <$> r) <*> f (_myA1 <$> r)+--+-- A grid is converted into a grate by using the 'Lens.Family2.over' function, and it is converted to a traversal by using the 'Lens.Family2.under' function.+--+-- /Note/: It is possible to build grids without even depending on @lens-family@ by expanding away the type synonym.+--+-- > myMaybes :: (Applicative f, Functor g) => (g (Maybe a) -> f (Maybe b)) -> g (MyRecord a) -> f (MyRecord b)+--+-- Unfortunately, there are no helper functions for making grids.+-- In most cases, you must make them by hand.+ -- * Documentation-    lens-  , iso+    adapter+  , lens+  , prism+  , grate   , setting+  , resetting -- * Types+  , Adapter, Adapter'+  , Prism, Prism'   , Lens, Lens'   , Traversal, Traversal'   , Setter, Setter'+  , Grate, Grate'+  , Resetter, Resetter'+  , LF.AdapterLike, LF.AdapterLike'   , LF.LensLike, LF.LensLike'+  , LF.GrateLike, LF.GrateLike'   , LF.Identical--- * Re-exports-  , Applicative   ) where -import Control.Applicative (Applicative) import qualified Lens.Family.Unchecked as LF -type Lens a a' b b' = forall f. Functor f => LF.LensLike f a a' b b'-type Lens' a b = forall f. Functor f => LF.LensLike' f a b+type Adapter s t a b = forall f g. (Functor f, Functor g) => LF.AdapterLike f g s t a b+type Adapter' s a = forall f g. (Functor f, Functor g) => LF.AdapterLike' f g s a -type Traversal a a' b b' = forall f. Applicative f => LF.LensLike f a a' b b'-type Traversal' a b = forall f. Applicative f => LF.LensLike' f a b+type Prism s t a b = forall f g. (Applicative f, Traversable g) => LF.AdapterLike f g s t a b+type Prism' s a = forall f g. (Applicative f, Traversable g) => LF.AdapterLike' f g s a -type Setter a a' b b' = forall f. LF.Identical f => LF.LensLike f a a' b b'-type Setter' a b = forall f. LF.Identical f => LF.LensLike' f a b+type Lens s t a b = forall f. Functor f => LF.LensLike f s t a b+type Lens' s a = forall f. Functor f => LF.LensLike' f s a --- | Build a lens from a @getter@ and @setter@ families.+type Traversal s t a b = forall f. Applicative f => LF.LensLike f s t a b+type Traversal' s a = forall f. Applicative f => LF.LensLike' f s a++type Setter s t a b = forall f. LF.Identical f => LF.LensLike f s t a b+type Setter' s a = forall f. LF.Identical f => LF.LensLike' f s a++type Grate s t a b = forall g. Functor g => LF.GrateLike g s t a b+type Grate' s a = forall g. Functor g => LF.GrateLike' g s a++type Resetter s t a b = forall g. LF.Identical g => LF.GrateLike g s t a b+type Resetter' s a = forall g. LF.Identical g => LF.GrateLike' g s a++-- | Build an adapter from an isomorphism family. --+-- /Caution/: In order for the generated adapter family to be well-defined, you must ensure that the two isomorphism laws hold:+--+-- * @yin . yang === id@+--+-- * @yang . yin === id@+adapter :: (s -> a) -- ^ yin+        -> (b -> t) -- ^ yang+        -> Adapter s t a b+adapter = LF.adapter++-- | Build a lens from a @getter@ and @setter@ family.+-- -- /Caution/: In order for the generated lens family to be well-defined, you must ensure that the three lens laws hold:--- --- * @getter (setter a b) === b@ ----- * @setter a (getter a) === a@+-- * @getter (setter s a) === a@ ----- * @setter (setter a b1) b2) === setter a b2@-lens :: (a -> b) -- ^ getter-     -> (a -> b' -> a') -- ^ setter-     -> Lens a a' b b'+-- * @setter s (getter s) === s@+--+-- * @setter (setter s a1) a2 === setter s a2@+lens :: (s -> a) -- ^ getter+     -> (s -> b -> t) -- ^ setter+     -> Lens s t a b lens = LF.lens --- | Build a lens from isomorphism families.+grate :: (((s -> a) -> b) -> t) -- ^ grater+      -> Grate s t a b+-- ^ Build a grate from a @grater@ family. ----- /Caution/: In order for the generated lens family to be well-defined, you must ensure that the two isomorphism laws hold:--- --- * @yin . yang === id@+-- /Caution/: In order for the generated grate family to be well-defined, you must ensure that the two grater laws hold: ----- * @yang . yin === id@-iso :: (a -> b) -- ^ yin-    -> (b' -> a') -- ^ yang-    -> Lens a a' b b'-iso = LF.iso+-- * @grater ($ s) === s@+--+-- * @grater (\k -> h (k . grater)) === grater (\k -> h ($ k))@+--+-- Note: The grater laws are that of an algebra for the parameterised continuation monad, `Lens.Family.PCont`.+grate = LF.grate +-- | Build a prism from a @matcher@ and @reviewer@ family.+--+-- /Caution/: In order for the generated prism family to be well-defined, you must ensure that the three prism laws hold:+--+-- * @matcher (reviewer b) === Right b@+--+-- * @(id ||| reviewer) (matcher s) === s@+--+-- * @left matcher (matcher s) === left Left (matcher s)@+prism :: (s -> Either t a) -- ^ matcher+      -> (b -> t) -- ^ reviewer+      -> Prism s t a b+prism = LF.prism+ -- | 'setting' promotes a \"semantic editor combinator\" to a modify-only lens. -- To demote a lens to a semantic edit combinator, use the section @(l %~)@ or @over l@ from "Lens.Family2". ----- >>> setting map . fstL %~ length $ [("The",0),("quick",1),("brown",1),("fox",2)]+-- >>> [("The",0),("quick",1),("brown",1),("fox",2)] & setting map . fstL %~ length -- [(3,0),(5,1),(5,1),(3,2)] ----- /Caution/: In order for the generated setter family to be well-defined, you must ensure that the two functors laws hold:--- +-- /Caution/: In order for the generated family to be well-defined, you must ensure that the two functors laws hold:+-- -- * @sec id === id@ -- -- * @sec f . sec g === sec (f . g)@-setting :: ((b -> b') -> a -> a') -- ^ sec (semantic editor combinator)-        -> Setter a a' b b'+setting :: ((a -> b) -> s -> t) -- ^ sec (semantic editor combinator)+        -> Setter s t a b setting = LF.setting++-- | 'resetting' promotes a \"semantic editor combinator\" to a form of grate that can only lift unary functions.+-- To demote a grate to a semantic edit combinator, use @under l@ from "Lens.Family2".+--+-- /Caution/: In order for the generated family to be well-defined, you must ensure that the two functors laws hold:+--+-- * @sec id === id@+--+-- * @sec f . sec g === sec (f . g)@+resetting :: ((a -> b) -> s -> t) -- ^ sec (semantic editor combinator)+        -> Resetter s t a b+resetting = LF.resetting