符号< $>是什么和< *>在哈斯克尔意味着什么?

时间:2015-04-03 18:58:51

标签: haskell

符号<$><*>的含义是什么?

另外,我找到了一些有关<$$>的信息。

2 个答案:

答案 0 :(得分:7)

这些运算符在Control.Applicative中定义。 <$>运算符只是fmap的中缀版本:

f <$> a = fmap f a

<*>Applicative类型类定义的一部分:

class Functor f => Applicative f where
    pure :: a -> f a
    (<*>) :: f (a -> b) -> f a -> f b

您可以使用hoogle更轻松地搜索Haskell函数和运算符。

Applicative类型类介于FunctorMonad之间:

class Functor where ...

class Functor f => Applicative f where ...

class Applicative m => Monad m where ...

(请注意,这是ApplicativeMonad之间的关系,仅在最近发布的GHC 7.10中强制执行。

申请人是遵循特定规则的结构。它比一个仿函数更强大但比一个monad更强大。具体而言,仿函数只能将单参数函数应用于结构中的值,返回包含新值但不包含新形状的新结构。规范示例为fmap (+1) [1,2,3] == [2,3,4],输入列表的长度始终与输出列表相同。使用applicatives,您可以跨多个结构应用多参数纯函数:

> (+) <$> [1, 2, 3] <*> [10, 20]
[11, 21, 12, 22, 13, 23]

输出列表的长度(&#34;形状&#34;)取决于输入列表的长度。但是,需要注意的是输出列表的长度不依赖于列表中的。这是monad添加到此层次结构的强大功能:

> print $ do a <- [1, 2, 3]; b <- replicate a 10; return (a + b)
[11, 12, 12, 13, 13, 13]

这里我们将两个结构组合在一起,其中一个具有&#34;形状&#34;这取决于另一个的价值。只有应用程序才能实现这一点,这就是为什么monads在Haskell中如此普遍存在的原因。但是,由于每个Monad都是Applicative,每ApplicativeFunctor,因此在使用Monad时,您仍然可以访问所有这些工具。

答案 1 :(得分:4)

<$>是fmap的同义词,<$>是中缀运算符。它通常用于应用函子的上下文中。

import Control.Applicative ((<$>)

-- (<$>), fmap :: Functor f => (a -> b) -> f a -> f b

example1 :: (Int -> Int) -> Maybe Int -> Maybe Int
example1 f g = f <$> g  -- f `fmap` (Just x) = Just (f x)
                        -- f `fmap` Nothing  = Nothing

另一方面,当你在一个仿函数的上下文中有一个函数并且想要将它应用于另一个仿函数上下文中的某个值时,<*>很有用,例如:

example2:: Maybe (Int -> Int) -> Maybe Int -> Maybe Int
example2 f g = f <*> g -- (Just f) <*> (Just x) = Just ( f x)
                       -- Nothing  <*> (Just x ) = Nothing
                       -- (Just f) <*> Nothing   = Nothing
                       -- Nothing <*>  Nothing   = Nothing

可以将其描绘为应用函数的运算符,同时考虑应用函数的上下文。

这些操作符将值和函数提升到执行操作的Functor的上下文中。