{-# OPTIONS_HADDOCK hide #-}
{-# LANGUAGE DerivingVia #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE GADTs #-}
{-# LANGUAGE LinearTypes #-}
{-# LANGUAGE NoImplicitPrelude #-}
{-# LANGUAGE RankNTypes #-}
{-# LANGUAGE TupleSections #-}
{-# LANGUAGE TypeOperators #-}
{-# LANGUAGE TypeApplications #-}

module Data.Functor.Linear.Internal.Traversable
  ( -- * Linear traversable hierarchy
    -- $ traversable
    Traversable(..)
  , mapM, sequenceA, for, forM
  , mapAccumL, mapAccumR
  ) where

import qualified Control.Functor.Linear.Internal.Class as Control
import qualified Control.Functor.Linear.Internal.State as Control
import qualified Control.Functor.Linear.Internal.Instances as Control
import qualified Data.Functor.Linear.Internal.Functor as Data
import qualified Data.Functor.Linear.Internal.Applicative as Data
import Data.Functor.Const
import Prelude.Linear.Internal
import Prelude (Maybe(..), Either(..))

-- $traversable

-- TODO: write the laws
-- TODO: maybe add a Foldable class between Functor and Traversable as well

-- | A linear data traversible is a functor of type @t a@ where you can apply a
-- linear effectful action of type @a %1-> f b@ on each value of type @a@ and
-- compose this to perform an action on the whole functor, resulting in a value
-- of type @f (t b)@.
--
-- To learn more about 'Traversable', see here:
--
--  * \"Applicative Programming with Effects\",
--    by Conor McBride and Ross Paterson,
--    /Journal of Functional Programming/ 18:1 (2008) 1-13, online at
--    <http://www.soi.city.ac.uk/~ross/papers/Applicative.html>.
--
--  * \"The Essence of the Iterator Pattern\",
--    by Jeremy Gibbons and Bruno Oliveira,
--    in /Mathematically-Structured Functional Programming/, 2006, online at
--    <http://web.comlab.ox.ac.uk/oucl/work/jeremy.gibbons/publications/#iterator>.
--
--  * \"An Investigation of the Laws of Traversals\",
--    by Mauro Jaskelioff and Ondrej Rypacek,
--    in /Mathematically-Structured Functional Programming/, 2012, online at
--    <http://arxiv.org/pdf/1202.2919>.
--
class Data.Functor t => Traversable t where
  {-# MINIMAL traverse | sequence #-}

  traverse :: Control.Applicative f => (a %1-> f b) -> t a %1-> f (t b)
  {-# INLINE traverse #-}
  traverse a %1 -> f b
f t a
x = t (f b) %1 -> f (t b)
forall (t :: * -> *) (f :: * -> *) a.
(Traversable t, Applicative f) =>
t (f a) %1 -> f (t a)
sequence ((a %1 -> f b) -> t a %1 -> t (f b)
forall (f :: * -> *) a b. Functor f => (a %1 -> b) -> f a %1 -> f b
Data.fmap a %1 -> f b
f t a
x)

  sequence :: Control.Applicative f => t (f a) %1-> f (t a)
  {-# INLINE sequence #-}
  sequence = (f a %1 -> f a) -> t (f a) %1 -> f (t a)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a %1 -> f b) -> t a %1 -> f (t b)
traverse f a %1 -> f a
forall a. a %1 -> a
id

mapM :: (Traversable t, Control.Monad m) => (a %1-> m b) -> t a %1-> m (t b)
mapM :: forall (t :: * -> *) (m :: * -> *) a b.
(Traversable t, Monad m) =>
(a %1 -> m b) -> t a %1 -> m (t b)
mapM = (a %1 -> m b) -> t a %1 -> m (t b)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a %1 -> f b) -> t a %1 -> f (t b)
traverse
{-# INLINE mapM #-}

sequenceA :: (Traversable t, Control.Applicative f) => t (f a) %1-> f (t a)
sequenceA :: forall (t :: * -> *) (f :: * -> *) a.
(Traversable t, Applicative f) =>
t (f a) %1 -> f (t a)
sequenceA = t (f a) %1 -> f (t a)
forall (t :: * -> *) (f :: * -> *) a.
(Traversable t, Applicative f) =>
t (f a) %1 -> f (t a)
sequence
{-# INLINE sequenceA #-}

for :: (Traversable t, Control.Applicative f) => t a %1-> (a %1-> f b) -> f (t b)
for :: forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
t a %1 -> (a %1 -> f b) -> f (t b)
for t a
t a %1 -> f b
f = (a %1 -> f b) -> t a %1 -> f (t b)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a %1 -> f b) -> t a %1 -> f (t b)
traverse a %1 -> f b
f t a
t
{-# INLINE for #-}

forM :: (Traversable t, Control.Monad m) => t a %1-> (a %1-> m b) -> m (t b)
forM :: forall (t :: * -> *) (m :: * -> *) a b.
(Traversable t, Monad m) =>
t a %1 -> (a %1 -> m b) -> m (t b)
forM = t a %1 -> (a %1 -> m b) -> m (t b)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
t a %1 -> (a %1 -> f b) -> f (t b)
for
{-# INLINE forM #-}

mapAccumL :: Traversable t => (a %1-> b %1-> (a,c)) -> a %1-> t b %1-> (a, t c)
mapAccumL :: forall (t :: * -> *) a b c.
Traversable t =>
(a %1 -> b %1 -> (a, c)) -> a %1 -> t b %1 -> (a, t c)
mapAccumL a %1 -> b %1 -> (a, c)
f a
s t b
t = (t c, a) %1 -> (a, t c)
forall a b. (a, b) %1 -> (b, a)
swap ((t c, a) %1 -> (a, t c)) %1 -> (t c, a) %1 -> (a, t c)
forall a b. (a %1 -> b) %1 -> a %1 -> b
$ State a (t c) %1 -> a %1 -> (t c, a)
forall s a. State s a %1 -> s %1 -> (a, s)
Control.runState ((b %1 -> StateT a Identity c) -> t b %1 -> State a (t c)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a %1 -> f b) -> t a %1 -> f (t b)
traverse (\b
b -> (a %1 -> (c, a)) %1 -> StateT a Identity c
forall (m :: * -> *) s a.
Applicative m =>
(s %1 -> (a, s)) %1 -> StateT s m a
Control.state ((a %1 -> (c, a)) %1 -> StateT a Identity c)
%1 -> (a %1 -> (c, a)) %1 -> StateT a Identity c
forall a b. (a %1 -> b) %1 -> a %1 -> b
$ \a
i -> (a, c) %1 -> (c, a)
forall a b. (a, b) %1 -> (b, a)
swap ((a, c) %1 -> (c, a)) %1 -> (a, c) %1 -> (c, a)
forall a b. (a %1 -> b) %1 -> a %1 -> b
$ a %1 -> b %1 -> (a, c)
f a
i b
b) t b
t) a
s

mapAccumR :: Traversable t => (a %1-> b %1-> (a,c)) -> a %1-> t b %1-> (a, t c)
mapAccumR :: forall (t :: * -> *) a b c.
Traversable t =>
(a %1 -> b %1 -> (a, c)) -> a %1 -> t b %1 -> (a, t c)
mapAccumR a %1 -> b %1 -> (a, c)
f a
s t b
t = (t c, a) %1 -> (a, t c)
forall a b. (a, b) %1 -> (b, a)
swap ((t c, a) %1 -> (a, t c)) %1 -> (t c, a) %1 -> (a, t c)
forall a b. (a %1 -> b) %1 -> a %1 -> b
$ StateR a (t c) %1 -> a %1 -> (t c, a)
forall s a. StateR s a %1 -> s %1 -> (a, s)
runStateR ((b %1 -> StateR a c) -> t b %1 -> StateR a (t c)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a %1 -> f b) -> t a %1 -> f (t b)
traverse (\b
b -> (a %1 -> (c, a)) %1 -> StateR a c
forall s a. (s %1 -> (a, s)) -> StateR s a
StateR ((a %1 -> (c, a)) %1 -> StateR a c)
%1 -> (a %1 -> (c, a)) %1 -> StateR a c
forall a b. (a %1 -> b) %1 -> a %1 -> b
$ \a
i -> (a, c) %1 -> (c, a)
forall a b. (a, b) %1 -> (b, a)
swap ((a, c) %1 -> (c, a)) %1 -> (a, c) %1 -> (c, a)
forall a b. (a %1 -> b) %1 -> a %1 -> b
$ a %1 -> b %1 -> (a, c)
f a
i b
b) t b
t) a
s

swap :: (a,b) %1-> (b,a)
swap :: forall a b. (a, b) %1 -> (b, a)
swap (a
x,b
y) = (b
y,a
x)

-- | A right-to-left state transformer
newtype StateR s a = StateR (s %1-> (a, s))
  deriving ((forall a b. (a %1 -> b) -> StateR s a %1 -> StateR s b)
-> Functor (StateR s)
forall a b. (a %1 -> b) -> StateR s a %1 -> StateR s b
forall s a b. (a %1 -> b) -> StateR s a %1 -> StateR s b
forall (f :: * -> *).
(forall a b. (a %1 -> b) -> f a %1 -> f b) -> Functor f
fmap :: forall a b. (a %1 -> b) -> StateR s a %1 -> StateR s b
$cfmap :: forall s a b. (a %1 -> b) -> StateR s a %1 -> StateR s b
Data.Functor, Functor (StateR s)
Functor (StateR s)
-> (forall a. a -> StateR s a)
-> (forall a b.
    StateR s (a %1 -> b) %1 -> StateR s a %1 -> StateR s b)
-> (forall a b c.
    (a %1 -> b %1 -> c)
    -> StateR s a %1 -> StateR s b %1 -> StateR s c)
-> Applicative (StateR s)
forall s. Functor (StateR s)
forall a. a -> StateR s a
forall s a. a -> StateR s a
forall a b. StateR s (a %1 -> b) %1 -> StateR s a %1 -> StateR s b
forall s a b.
StateR s (a %1 -> b) %1 -> StateR s a %1 -> StateR s b
forall a b c.
(a %1 -> b %1 -> c) -> StateR s a %1 -> StateR s b %1 -> StateR s c
forall s a b c.
(a %1 -> b %1 -> c) -> StateR s a %1 -> StateR s b %1 -> StateR s c
forall (f :: * -> *).
Functor f
-> (forall a. a -> f a)
-> (forall a b. f (a %1 -> b) %1 -> f a %1 -> f b)
-> (forall a b c. (a %1 -> b %1 -> c) -> f a %1 -> f b %1 -> f c)
-> Applicative f
liftA2 :: forall a b c.
(a %1 -> b %1 -> c) -> StateR s a %1 -> StateR s b %1 -> StateR s c
$cliftA2 :: forall s a b c.
(a %1 -> b %1 -> c) -> StateR s a %1 -> StateR s b %1 -> StateR s c
<*> :: forall a b. StateR s (a %1 -> b) %1 -> StateR s a %1 -> StateR s b
$c<*> :: forall s a b.
StateR s (a %1 -> b) %1 -> StateR s a %1 -> StateR s b
pure :: forall a. a -> StateR s a
$cpure :: forall s a. a -> StateR s a
Data.Applicative) via Control.Data (StateR s)

runStateR :: StateR s a %1-> s %1-> (a, s)
runStateR :: forall s a. StateR s a %1 -> s %1 -> (a, s)
runStateR (StateR s %1 -> (a, s)
f) = s %1 -> (a, s)
f

instance Control.Functor (StateR s) where
  fmap :: forall a b. (a %1 -> b) %1 -> StateR s a %1 -> StateR s b
fmap a %1 -> b
f (StateR s %1 -> (a, s)
x) = (s %1 -> (b, s)) %1 -> StateR s b
forall s a. (s %1 -> (a, s)) -> StateR s a
StateR ((s %1 -> (b, s)) %1 -> StateR s b)
%1 -> (s %1 -> (b, s)) %1 -> StateR s b
forall a b. (a %1 -> b) %1 -> a %1 -> b
$ (\(a
a, s
s') -> (a %1 -> b
f a
a, s
s')) ((a, s) %1 -> (b, s)) %1 -> (s %1 -> (a, s)) %1 -> s %1 -> (b, s)
forall b c a. (b %1 -> c) %1 -> (a %1 -> b) %1 -> a %1 -> c
. s %1 -> (a, s)
x

instance Control.Applicative (StateR s) where
  pure :: forall a. a %1 -> StateR s a
pure a
x = (s %1 -> (a, s)) %1 -> StateR s a
forall s a. (s %1 -> (a, s)) -> StateR s a
StateR ((s %1 -> (a, s)) %1 -> StateR s a)
%1 -> (s %1 -> (a, s)) %1 -> StateR s a
forall a b. (a %1 -> b) %1 -> a %1 -> b
$ \s
s -> (a
x,s
s)
  StateR s %1 -> (a %1 -> b, s)
f <*> :: forall a b. StateR s (a %1 -> b) %1 -> StateR s a %1 -> StateR s b
<*> StateR s %1 -> (a, s)
x = (s %1 -> (b, s)) %1 -> StateR s b
forall s a. (s %1 -> (a, s)) -> StateR s a
StateR ((a, (a %1 -> b, s)) %1 -> (b, s)
forall a b s. (a, (a %1 -> b, s)) %1 -> (b, s)
go ((a, (a %1 -> b, s)) %1 -> (b, s))
%1 -> ((a, s) %1 -> (a, (a %1 -> b, s))) %1 -> (a, s) %1 -> (b, s)
forall b c a. (b %1 -> c) %1 -> (a %1 -> b) %1 -> a %1 -> c
. (s %1 -> (a %1 -> b, s)) %1 -> (a, s) %1 -> (a, (a %1 -> b, s))
forall (f :: * -> *) a b.
Functor f =>
(a %1 -> b) %1 -> f a %1 -> f b
Control.fmap s %1 -> (a %1 -> b, s)
f ((a, s) %1 -> (b, s)) %1 -> (s %1 -> (a, s)) %1 -> s %1 -> (b, s)
forall b c a. (b %1 -> c) %1 -> (a %1 -> b) %1 -> a %1 -> c
. s %1 -> (a, s)
x)
    where go :: (a, (a %1-> b, s)) %1-> (b, s)
          go :: forall a b s. (a, (a %1 -> b, s)) %1 -> (b, s)
go (a
a, (a %1 -> b
h, s
s'')) = (a %1 -> b
h a
a, s
s'')

------------------------
-- Standard instances --
------------------------

instance Traversable [] where
  traverse :: forall (f :: * -> *) a b.
Applicative f =>
(a %1 -> f b) -> [a] %1 -> f [b]
traverse a %1 -> f b
_f [] = [b] %1 -> f [b]
forall (f :: * -> *) a. Applicative f => a %1 -> f a
Control.pure []
  traverse a %1 -> f b
f (a
a : [a]
as) = (:) (b %1 -> [b] %1 -> [b]) %1 -> f b %1 -> f ([b] %1 -> [b])
forall (f :: * -> *) a b.
Functor f =>
(a %1 -> b) %1 -> f a %1 -> f b
Control.<$> a %1 -> f b
f a
a f ([b] %1 -> [b]) %1 -> f [b] %1 -> f [b]
forall (f :: * -> *) a b.
Applicative f =>
f (a %1 -> b) %1 -> f a %1 -> f b
Control.<*> (a %1 -> f b) -> [a] %1 -> f [b]
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a %1 -> f b) -> t a %1 -> f (t b)
traverse a %1 -> f b
f [a]
as

instance Traversable ((,) a) where
  sequence :: forall (f :: * -> *) a. Applicative f => (a, f a) %1 -> f (a, a)
sequence (a
a, f a
fb) = (a
a,) (a %1 -> (a, a)) %1 -> f a %1 -> f (a, a)
forall (f :: * -> *) a b.
Functor f =>
(a %1 -> b) %1 -> f a %1 -> f b
Control.<$> f a
fb

instance Traversable Maybe where
  sequence :: forall (f :: * -> *) a.
Applicative f =>
Maybe (f a) %1 -> f (Maybe a)
sequence Maybe (f a)
Nothing = Maybe a %1 -> f (Maybe a)
forall (f :: * -> *) a. Applicative f => a %1 -> f a
Control.pure Maybe a
forall a. Maybe a
Nothing
  sequence (Just f a
x) = (a %1 -> Maybe a) %1 -> f a %1 -> f (Maybe a)
forall (f :: * -> *) a b.
Functor f =>
(a %1 -> b) %1 -> f a %1 -> f b
Control.fmap a %1 -> Maybe a
forall a. a -> Maybe a
Just f a
x

instance Traversable (Const a) where
  sequence :: forall (f :: * -> *) a.
Applicative f =>
Const a (f a) %1 -> f (Const a a)
sequence (Const a
x) = Const a a %1 -> f (Const a a)
forall (f :: * -> *) a. Applicative f => a %1 -> f a
Control.pure (a %1 -> Const a a
forall {k} a (b :: k). a -> Const a b
Const a
x)

instance Traversable (Either a) where
  sequence :: forall (f :: * -> *) a.
Applicative f =>
Either a (f a) %1 -> f (Either a a)
sequence (Left a
x) = Either a a %1 -> f (Either a a)
forall (f :: * -> *) a. Applicative f => a %1 -> f a
Control.pure (a %1 -> Either a a
forall a b. a -> Either a b
Left a
x)
  sequence (Right f a
x) = a %1 -> Either a a
forall a b. b -> Either a b
Right (a %1 -> Either a a) %1 -> f a %1 -> f (Either a a)
forall (f :: * -> *) a b.
Functor f =>
(a %1 -> b) %1 -> f a %1 -> f b
Control.<$> f a
x