module Control.Monad.Parallel where

import HPrelude

class (Applicative (Parallel m), Monad m) => MonadParallel m where
  type Parallel m :: Type -> Type
  parallel :: m a -> Parallel m a
  sequential :: Parallel m a -> m a

instance MonadParallel IO where
  type Parallel IO = Concurrently IO
  parallel :: forall a. IO a -> Parallel IO a
parallel = IO a -> Concurrently IO a
IO a -> Parallel IO a
forall (m :: * -> *) a. m a -> Concurrently m a
Concurrently
  sequential :: forall a. Parallel IO a -> IO a
sequential = Concurrently IO a -> IO a
Parallel IO a -> IO a
forall (m :: * -> *) a. Concurrently m a -> m a
runConcurrently

parSequence :: (MonadParallel m, Traversable t) => t (m a) -> m (t a)
parSequence :: forall (m :: * -> *) (t :: * -> *) a.
(MonadParallel m, Traversable t) =>
t (m a) -> m (t a)
parSequence = Parallel m (t a) -> m (t a)
forall a. Parallel m a -> m a
forall (m :: * -> *) a. MonadParallel m => Parallel m a -> m a
sequential (Parallel m (t a) -> m (t a))
-> (t (m a) -> Parallel m (t a)) -> t (m a) -> m (t a)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (m a -> Parallel m a) -> t (m a) -> Parallel m (t a)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a -> f b) -> t a -> f (t b)
forall (f :: * -> *) a b.
Applicative f =>
(a -> f b) -> t a -> f (t b)
traverse m a -> Parallel m a
forall a. m a -> Parallel m a
forall (m :: * -> *) a. MonadParallel m => m a -> Parallel m a
parallel

parSequence_ :: (MonadParallel m, Traversable t) => t (m a) -> m ()
parSequence_ :: forall (m :: * -> *) (t :: * -> *) a.
(MonadParallel m, Traversable t) =>
t (m a) -> m ()
parSequence_ = m (t a) -> m ()
forall (f :: * -> *) a. Functor f => f a -> f ()
void (m (t a) -> m ()) -> (t (m a) -> m (t a)) -> t (m a) -> m ()
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Parallel m (t a) -> m (t a)
forall a. Parallel m a -> m a
forall (m :: * -> *) a. MonadParallel m => Parallel m a -> m a
sequential (Parallel m (t a) -> m (t a))
-> (t (m a) -> Parallel m (t a)) -> t (m a) -> m (t a)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (m a -> Parallel m a) -> t (m a) -> Parallel m (t a)
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a -> f b) -> t a -> f (t b)
forall (f :: * -> *) a b.
Applicative f =>
(a -> f b) -> t a -> f (t b)
traverse m a -> Parallel m a
forall a. m a -> Parallel m a
forall (m :: * -> *) a. MonadParallel m => m a -> Parallel m a
parallel