PyR*_*lez 15 continuations haskell typeclass applicative continuation-passing
我们可以将continuation monad变换器定义为
data Cont r m a = Cont {run :: (a -> m r) -> m r}
Run Code Online (Sandbox Code Playgroud)
Cont r m如果m是Alternativevia 的成员,我们可以给出Alternative实例
empty = Cont $ \f -> empty
ca <|> cb = Cont $ \f -> run ca f <|> run cb f
Run Code Online (Sandbox Code Playgroud)
然后允许some并many采用他们的默认方法.我的问题是,我们可以定义some并many在以下方面m的some和many,而不是默认的定义是什么?显而易见的选择
some ca = Cont $ \f -> some $ run ca f
many ca = Cont $ \f -> many $ run ca f
Run Code Online (Sandbox Code Playgroud)
显然不起作用(他们甚至不打字检查).还有其他方法可以使用它们(如果我们m还需要一个monad,那很好)?
供参考,some并且many必须至少解决方程式:
some v = (:) <$> v <*> many vmany v = some v <|> pure []假设some :: m a -> m [a]并且many :: m a -> [a]满足这个法则,那么应该some :: Cont r m a -> Cont r m [a]和many :: Cont r m a -> Cont r m [a].
不。
不存在从
(forall a. f a -> f [a]) ->
(forall r. ((a -> f r) -> f r)) -> (([a] -> f r) -> f r)`
Run Code Online (Sandbox Code Playgroud)
它以一种有趣的方式利用了它的论点。
唯一forall a. f a -> f [a]可以应用的地方是f r. 这些是 的结果(a -> f r) -> f r,就像您的“明显的选择”中一样,并且([a] -> f r)。这留下了类型的结果f [r]。forall r. Alternative f => f [r]使用 a生成 an唯一可以做的事情就是使用某个部分函数f r将 a从自然数索引到其他不更大的自然数。f [r]forall r. [r] -> r