在绑定方面,如何定义应用? [英] How to define apply in terms of bind?

查看:18
本文介绍了在绑定方面,如何定义应用?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在Haskell中,应用程序被认为比函数器更强,这意味着我们可以使用应用程序Like来定义函数器

-- Functor
fmap :: (a -> b) -> f a -> f b
fmap f fa = pure f <*> fa

和Monad被认为比Applicative&;Functor更强,这意味着。

-- Functor
fmap :: (a -> b) -> f a -> f b
fmap f fa = fa >>= return . f

-- Applicative
pure :: a -> f a
pure = return

(<*>) :: f (a -> b) -> f a -> f b
(<*>) = ???  -- Can we define this in terms return & bind? without using "ap" 

我读到过单体是用于排序操作的。但我觉得Monad唯一能做的就是加入或扁平化,而它的其余功能来自于Applicative。

join :: m (m a) -> m a
-- & where is the sequencing in this part? I don't get it.

如果Monad真的用于排序操作,那么为什么我们可以定义应用程序(不被认为是严格按顺序操作的,某种并行计算)?

As Monad是内函子范畴中的么半群。也有交换么半群,它们不一定按顺序工作。这意味着交换么半群的Monad实例也需要排序?

编辑: 我发现了一个很棒的页面 http://wiki.haskell.org/What_a_Monad_is_not

推荐答案

如果Monad真的用于排序操作,那么为什么我们可以定义应用程序(不被认为是严格按顺序操作的,某种并行计算)?

不完全是。所有的单数词都是补语,但只有部分补语是单数词。因此,在给定Monad的情况下,您始终可以根据bindreturn来定义应用实例,但如果您所拥有的只是应用实例,则在没有更多信息的情况下,您无法定义Monad。

Monad的应用实例如下所示:

instance (Monad m) => Applicative m where
   pure = return
   f <*> v = do
      f' <- f
      v' <- v
      return $ f' v'

当然,这将按顺序计算fv,因为它是一个单体,而这正是单体所做的。如果此应用程序不按顺序执行操作,则它不是单数。

当然,现代Haskell以相反的方式定义了这一点:Applicative类型类是Functor的子集,因此如果您有Functor并且您可以定义(<*>),那么您就可以创建Applicative实例。Monad又被定义为Applicative的子集,所以如果您有一个Applicative实例,并且您可以定义(>>=),那么您就可以创建一个Monad实例。但您不能用(<*>)来定义(>>=)

有关详细信息,请参阅Typeclassopedia

这篇关于在绑定方面,如何定义应用?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆