[英]Monad laws for an applicative-based formulation
Normally in Haskell we define Monad
s in terms of return
and >>=
. 通常在Haskell中我们用return
和>>=
来定义Monad
s。 Sometimes it's convenient to decompose >>=
into fmap
and join
. 有时将>>=
分解为fmap
并join
是很方便的。 The Monad
laws for these two formulations are well known and fairly intuitive, once you get used to them. 一旦你习惯了这两种配方的Monad
法则是众所周知的并且相当直观。
There's another way to define monads, in terms of an Applicative
functor: 根据Applicative
仿函数,还有另一种定义monad的方法:
class Applicative f => MyMonad f where
myJoin :: f (f a) -> f a
I'm wondering about the laws for this kind of formulation. 我想知道这种配方的法律。 Obviously, we could just adapt the fmap
+ join
laws, as follows (I am not sure the names are particularly apt, but oh well): 显然,我们可以调整fmap
+ join
法则,如下所示(我不确定这些名称是否特别fmap
,但是很好):
myJoin . myJoin = myJoin . (pure myJoin <*>) ('Associativity')
myJoin . pure = myJoin . (pure pure <*>) = id ('Identity')
Clearly these conditions are sufficient for pure
, (<*>)
, and myJoin
to form a monad (in the sense that they guarantee that m `myBind` f = myJoin (pure f <*> m)
will be a well-behaved >>=
). 很明显,这些条件对于pure
(<*>)
和myJoin
足以构成一个monad(从某种意义上说,他们保证m `myBind` f = myJoin (pure f <*> m)
将是一个表现良好的>>=
)。 But are they necessary as well? 但它们也是必要的吗? It seems at least possible that the additional structure that Applicative
supports above and beyond Functor
might allow us to simplify these laws -- in other words, that some feature of the above laws might be otiose given that it is known that pure
and (<*>)
already satisfy the Applicative
laws. 至少有可能的是, Applicative
支持以上和Functor
之外的其他结构可能允许我们简化这些法则 - 换句话说,上述法律的某些特征可能是非常的,因为已知pure
和(<*>)
已满足Applicative
法律。
(In case you're wondering why we'd even go to the trouble of bothering with this formulation given either of the two standard possibilities: I'm not sure it's all that useful or perspicuous in programming contexts, but it turns out to be so when you use Monad
s to do natural langauge semantics .) (如果你想知道为什么我们甚至会遇到困扰这个公式的两种标准可能性:我不确定它在编程环境中是否有用或显而易见,但事实证明是所以当你使用Monad
s 做自然语言语义时 。)
The identity law is much easier to write 身份法更容易编写
join . fmap pure = join . pure = id
The traditional monad right identity law follows immediately from the definition of >>=
. 传统的monad权利身份法立即遵循>>=
的定义。 The left identity law uses an Applicative
law 左侧身份法使用Applicative
法律
m >>= k = join (fmap k m)
-- proof for right identity
m >>= return = m
join (fmap pure m) = m -- definition of >>=
id m = m -- identity
m = m -- definition of id
-- proof for left identity
return a >>= f = f a
join (fmap f (pure a)) = f a -- definitions of >>= and return
join (pure (f a)) = f a -- fmap f . pure = pure . f
id (f a) = f a -- identity
f a = f a -- definition of id
The interesting law for a relationship between Applicative
and Monad
is Applicative
和Monad
之间关系的有趣法则是
(<*>) = ap
-- or
m1 <*> m2 = m1 >>= (\x1 -> m2 >>= \x2 -> return (x1 x2)) -- definition of ap
In terms of Applicative
and join
this is 在Applicative
和join
方面,这是
m1 <*> m2 = join (fmap (\x1 -> fmap x1 m2) m1)
-- proof
m1 <*> m2 = join (fmap (\x1 -> m2 >>= \x2 -> return (x1 x2)) m1) -- definition of ap
m1 <*> m2 = join (fmap (\x1 -> join (fmap (\x2 -> return (x1 x2)) m2)) m1) -- definition of >>=
m1 <*> m2 = join (fmap (\x1 -> join (fmap (\x2 -> pure (x1 x2)) m2)) m1) -- return = pure
m1 <*> m2 = join (fmap (\x1 -> join (fmap (pure . x1) m2)) m1)
m1 <*> m2 = join (fmap (\x1 -> join (fmap pure (fmap x1 m2))) m1) -- fmap (f . g) = fmap f . fmap g
m1 <*> m2 = join (fmap (\x1 -> fmap x1 m2) m1) -- identity
There might be a more elegant way to write this. 可能有更优雅的方式来写这个。
I haven't found a way to show that the Monad
is associative based on 我还没有找到一种方法来表明Monad
是基于联想的
Functor
and Applicative
laws - particularly composition of <*>
Functor
和Applicative
Functor
- 特别是<*>
join . fmap pure = join . pure = id
身份join . fmap pure = join . pure = id
join . fmap pure = join . pure = id
(<*>) = ap
and I'm not sure if it's true. 我不确定这是不是真的。 I think you need the associative law join . join = join . fmap join
我认为你需要联想法join . join = join . fmap join
join . join = join . fmap join
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.