packages feed

deferred-folds 0.1 → 0.2

raw patch · 3 files changed

+95/−95 lines, 3 filesPVP ok

version bump matches the API change (PVP)

API changes (from Hackage documentation)

- DeferredFolds.ToBeFoldled: ToBeFoldled :: (forall output. (output -> input -> output) -> output -> output) -> ToBeFoldled input
- DeferredFolds.ToBeFoldled: fold :: Fold input output -> ToBeFoldled input -> output
- DeferredFolds.ToBeFoldled: foldable :: Foldable foldable => foldable a -> ToBeFoldled a
- DeferredFolds.ToBeFoldled: foldl' :: (output -> input -> output) -> output -> ToBeFoldled input -> output
- DeferredFolds.ToBeFoldled: instance Data.Semigroup.Semigroup (DeferredFolds.ToBeFoldled.ToBeFoldled a)
- DeferredFolds.ToBeFoldled: instance GHC.Base.Alternative DeferredFolds.ToBeFoldled.ToBeFoldled
- DeferredFolds.ToBeFoldled: instance GHC.Base.Applicative DeferredFolds.ToBeFoldled.ToBeFoldled
- DeferredFolds.ToBeFoldled: instance GHC.Base.Functor DeferredFolds.ToBeFoldled.ToBeFoldled
- DeferredFolds.ToBeFoldled: instance GHC.Base.Monad DeferredFolds.ToBeFoldled.ToBeFoldled
- DeferredFolds.ToBeFoldled: instance GHC.Base.MonadPlus DeferredFolds.ToBeFoldled.ToBeFoldled
- DeferredFolds.ToBeFoldled: instance GHC.Base.Monoid (DeferredFolds.ToBeFoldled.ToBeFoldled a)
- DeferredFolds.ToBeFoldled: newtype ToBeFoldled input
+ DeferredFolds.FoldlView: FoldlView :: (forall output. (output -> input -> output) -> output -> output) -> FoldlView input
+ DeferredFolds.FoldlView: fold :: Fold input output -> FoldlView input -> output
+ DeferredFolds.FoldlView: foldable :: Foldable foldable => foldable a -> FoldlView a
+ DeferredFolds.FoldlView: foldl' :: (output -> input -> output) -> output -> FoldlView input -> output
+ DeferredFolds.FoldlView: instance Data.Semigroup.Semigroup (DeferredFolds.FoldlView.FoldlView a)
+ DeferredFolds.FoldlView: instance GHC.Base.Alternative DeferredFolds.FoldlView.FoldlView
+ DeferredFolds.FoldlView: instance GHC.Base.Applicative DeferredFolds.FoldlView.FoldlView
+ DeferredFolds.FoldlView: instance GHC.Base.Functor DeferredFolds.FoldlView.FoldlView
+ DeferredFolds.FoldlView: instance GHC.Base.Monad DeferredFolds.FoldlView.FoldlView
+ DeferredFolds.FoldlView: instance GHC.Base.MonadPlus DeferredFolds.FoldlView.FoldlView
+ DeferredFolds.FoldlView: instance GHC.Base.Monoid (DeferredFolds.FoldlView.FoldlView a)
+ DeferredFolds.FoldlView: newtype FoldlView input

Files

deferred-folds.cabal view
@@ -1,9 +1,9 @@ name:   deferred-folds version:-  0.1+  0.2 category:-  Fold+  Folding synopsis:   Abstractions over deferred folds homepage:@@ -39,7 +39,7 @@   default-language:     Haskell2010   exposed-modules:-    DeferredFolds.ToBeFoldled+    DeferredFolds.FoldlView   other-modules:     DeferredFolds.Prelude   build-depends:
+ library/DeferredFolds/FoldlView.hs view
@@ -0,0 +1,92 @@+module DeferredFolds.FoldlView+where++import DeferredFolds.Prelude+import qualified DeferredFolds.Prelude as A+++{-|+A projection on data, which only knows how to execute a strict left-fold.++It is a monad and a monoid, and is very useful for+efficiently aggregating the projections on data intended for left-folding,+since its concatenation (`<>`) has complexity of @O(1)@.++[Intuition]++The intuition of what this abstraction is all about can be derived from lists.++Let's consider the `Data.List.foldl'` function for lists:++>foldl' :: (b -> a -> b) -> b -> [a] -> b++If we reverse its parameters we get++>foldl' :: [a] -> (b -> a -> b) -> b -> b++Which in Haskell is essentially the same as++>foldl' :: [a] -> (forall b. (b -> a -> b) -> b -> b)++We can isolate that part into an abstraction:++>newtype FoldlView a = FoldlView (forall b. (b -> a -> b) -> b -> b)++Then we get to this simple morphism:++>foldl' :: [a] -> FoldlView a++-}+newtype FoldlView input =+  FoldlView (forall output. (output -> input -> output) -> output -> output)++deriving instance Functor FoldlView++instance Applicative FoldlView where+  pure x =+    FoldlView (\ step init -> step init x)+  (<*>) = ap++instance Alternative FoldlView where+  empty =+    FoldlView (const id)+  {-# INLINE (<|>) #-}+  (<|>) (FoldlView left) (FoldlView right) =+    FoldlView (\ step init -> right step (left step init))++instance Monad FoldlView where+  return = pure+  (>>=) (FoldlView left) rightK =+    FoldlView $ \ step init ->+    let+      newStep output x =+        case rightK x of+          FoldlView right ->+            right step output+      in left newStep init++instance MonadPlus FoldlView where+  mzero = empty+  mplus = (<|>)++instance Semigroup (FoldlView a) where+  (<>) = (<|>)++instance Monoid (FoldlView a) where+  mempty = empty+  mappend = (<>)++{-| Perform a strict left fold -}+{-# INLINE foldl' #-}+foldl' :: (output -> input -> output) -> output -> FoldlView input -> output+foldl' step init (FoldlView run) = run step init++{-| Apply a Gonzalez fold -}+{-# INLINE fold #-}+fold :: Fold input output -> FoldlView input -> output+fold (Fold step init extract) (FoldlView run) = extract (run step init)++{-| Construct from any foldable -}+{-# INLINE foldable #-}+foldable :: Foldable foldable => foldable a -> FoldlView a+foldable foldable = FoldlView (\ step init -> A.foldl' step init foldable)
− library/DeferredFolds/ToBeFoldled.hs
@@ -1,92 +0,0 @@-module DeferredFolds.ToBeFoldled-where--import DeferredFolds.Prelude-import qualified DeferredFolds.Prelude as A---{-|-A projection on data, which only knows how to execute a strict left-fold.--It is a monad and a monoid, and is very useful for-efficiently aggregating the projections on data intended for left-folding,-since its concatenation (`<>`) has complexity of @O(1)@.--[Intuition]--The intuition of what this abstraction is all about can be derived from lists.--Let's consider the `Data.List.foldl'` function for lists:-->foldl' :: (b -> a -> b) -> b -> [a] -> b--If we reverse its parameters we get-->foldl' :: [a] -> (b -> a -> b) -> b -> b--Which in Haskell is essentially the same as-->foldl' :: [a] -> (forall b. (b -> a -> b) -> b -> b)--We can isolate that part into an abstraction:-->newtype ToBeFoldled a = ToBeFoldled (forall b. (b -> a -> b) -> b -> b)--Then we get to this simple morphism:-->foldl' :: [a] -> ToBeFoldled a---}-newtype ToBeFoldled input =-  ToBeFoldled (forall output. (output -> input -> output) -> output -> output)--deriving instance Functor ToBeFoldled--instance Applicative ToBeFoldled where-  pure x =-    ToBeFoldled (\ step init -> step init x)-  (<*>) = ap--instance Alternative ToBeFoldled where-  empty =-    ToBeFoldled (const id)-  {-# INLINE (<|>) #-}-  (<|>) (ToBeFoldled left) (ToBeFoldled right) =-    ToBeFoldled (\ step init -> right step (left step init))--instance Monad ToBeFoldled where-  return = pure-  (>>=) (ToBeFoldled left) rightK =-    ToBeFoldled $ \ step init ->-    let-      newStep output x =-        case rightK x of-          ToBeFoldled right ->-            right step output-      in left newStep init--instance MonadPlus ToBeFoldled where-  mzero = empty-  mplus = (<|>)--instance Semigroup (ToBeFoldled a) where-  (<>) = (<|>)--instance Monoid (ToBeFoldled a) where-  mempty = empty-  mappend = (<>)--{-| Perform a strict left fold -}-{-# INLINE foldl' #-}-foldl' :: (output -> input -> output) -> output -> ToBeFoldled input -> output-foldl' step init (ToBeFoldled run) = run step init--{-| Apply a Gonzalez fold -}-{-# INLINE fold #-}-fold :: Fold input output -> ToBeFoldled input -> output-fold (Fold step init extract) (ToBeFoldled run) = extract (run step init)--{-| Construct from any foldable -}-{-# INLINE foldable #-}-foldable :: Foldable foldable => foldable a -> ToBeFoldled a-foldable foldable = ToBeFoldled (\ step init -> A.foldl' step init foldable)