-
Notifications
You must be signed in to change notification settings - Fork 0
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Consider introducing an Evaluation
monad
#17
Comments
Here's a plan, albeit a half-baked one still. We can make a class class Monad m => MonadEvaluate m where
evaluate :: a -> m a Evidently, Now, if we have something that can be purely evaluated, then we can define it's eval function polymorphically To be able to do that, we can generalise the class MonadEvaluate m => EvalIn m a where
type Result a
eval :: a -> m (Result a)
type EvalIO = EvalIn IO
type Eval = EvalIn Evaluation (mostly equivalently, we could have In the pure function, we would require My big question, based on these thoughts, is whether we can replace withAlteringIO :: EvalIO a => … -> a -> IO (Result a) with withAlteringM :: EvalIn m a => … a -> m (Result a) Which, together with an instance instance EvalIn m (m a) would allow for convenient composition of several One thing that is slightly unsatisfactory, is that we would use an An idea: if we actually define the A smaller question (which may be irrelevant according to previous paragraph) is whether it's possible to define the class Eval a where
data Thunk a
type Result a
-- | Evaluating the @eval x@ thunk executes the evaluation strategy.
eval :: a -> Thunk a
extractEval :: Thunk a -> Result a
newtype Seq a = Seq a
deriving anyclass (EvalIO)
instance SeqIsEval a => Eval (Seq a) where
newtype Thunk (Seq a) = SeqThunk a
type Result (Seq a) = a
eval (Seq x) = SeqThunk x
extractEval (SeqThunk x) = x This suggest that, maybe |
An issue of allowing |
The
Evaluation
(possible alternative nameStrategy
) monad would have a single primitiveevaluate
(the same as theIO
monad. In fact, under the hood, it would possibly be theIO
monad, though maybe there is a pure solution).The idea would be that the
Evaluation
monad would support a (safe)run :: Evaluation a -> a
function, contrary to theIO
monad.It may be less clunky to use than the
Thunk
/extractEval
approach that I currently use. On the other hand, it may make it harder to deal with strict types.Something that I would love to get out of this is to be able to unify somehow the classes
Eval
andEvalIO
(the latter being introduced by #16 ). But the difficulty remains thatEvalIO (IO a)
must hold andEval (IO a)
absolutely mustn't. How can these be conciliated?The text was updated successfully, but these errors were encountered: