module PercentEncoding.MonadPlus where

import Platform.Prelude hiding (scanl)

{-# INLINE scanl #-}
scanl :: (MonadPlus m) => (a -> b -> a) -> a -> m b -> m a
scanl :: forall (m :: * -> *) a b.
MonadPlus m =>
(a -> b -> a) -> a -> m b -> m a
scanl a -> b -> a
step a
start m b
subaction =
  a -> m a
loop a
start
  where
    loop :: a -> m a
loop a
state =
      m a -> m a -> m a
forall a. m a -> m a -> m a
forall (m :: * -> *) a. MonadPlus m => m a -> m a -> m a
mplus
        ( do
            b
element <- m b
subaction
            a -> m a
loop (a -> m a) -> a -> m a
forall a b. (a -> b) -> a -> b
$! a -> b -> a
step a
state b
element
        )
        (a -> m a
forall a. a -> m a
forall (m :: * -> *) a. Monad m => a -> m a
return a
state)

{-# INLINE scanl1 #-}
scanl1 :: (MonadPlus m) => (a -> a -> a) -> m a -> m a
scanl1 :: forall (m :: * -> *) a. MonadPlus m => (a -> a -> a) -> m a -> m a
scanl1 a -> a -> a
step m a
subaction = do
  a
start <- m a
subaction
  (a -> a -> a) -> a -> m a -> m a
forall (m :: * -> *) a b.
MonadPlus m =>
(a -> b -> a) -> a -> m b -> m a
scanl a -> a -> a
step a
start m a
subaction

{-# INLINE scanlM #-}
scanlM :: (MonadPlus m) => (a -> b -> m a) -> a -> m b -> m a
scanlM :: forall (m :: * -> *) a b.
MonadPlus m =>
(a -> b -> m a) -> a -> m b -> m a
scanlM a -> b -> m a
step a
start m b
subaction =
  a -> m a
loop a
start
  where
    loop :: a -> m a
loop a
state =
      m (m a) -> m a
forall (m :: * -> *) a. Monad m => m (m a) -> m a
join
        ( m (m a) -> m (m a) -> m (m a)
forall a. m a -> m a -> m a
forall (m :: * -> *) a. MonadPlus m => m a -> m a -> m a
mplus
            ( do
                b
element <- m b
subaction
                return (a -> b -> m a
step a
state b
element m a -> (a -> m a) -> m a
forall a b. m a -> (a -> m b) -> m b
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= a -> m a
loop)
            )
            (m a -> m (m a)
forall a. a -> m a
forall (m :: * -> *) a. Monad m => a -> m a
return (a -> m a
forall a. a -> m a
forall (m :: * -> *) a. Monad m => a -> m a
return a
state))
        )

{-# INLINE scan #-}
scan :: (MonadPlus m, Monoid a) => m a -> m a
scan :: forall (m :: * -> *) a. (MonadPlus m, Monoid a) => m a -> m a
scan = (a -> a -> a) -> a -> m a -> m a
forall (m :: * -> *) a b.
MonadPlus m =>
(a -> b -> a) -> a -> m b -> m a
scanl a -> a -> a
forall a. Monoid a => a -> a -> a
mappend a
forall a. Monoid a => a
mempty