Haskell 中的索引函子到底是什么,它的用法是什么?
What is exactly an indexed functor in Haskell and what are its usages?
在 Haskell 中研究函子时,我想出了 Functor.Indexed type of functor. This functor defines an operation called imap
. I didn't understood its definition and imap
signature: imap :: (a -> b) -> f j k a -> f j k b
. I tried to find it s formal definition and found only this: http://ncatlab.org/nlab/show/indexed+functor 。但它真的对我一点帮助都没有。那么有人可以用更简单的话来澄清这种函子吗?我应该在什么情况下使用它?谢谢。
用 spacesuitburritoesque 措辞来说,索引仿函数是“一个还包含映射的容器”。 IE。一个值 f j k a
将“包含”某种态射 j -> k
(不一定是函数,可以是更一般的箭头) 以及 类型的值=20=].
对于那些 a
值,容器显然是一个函子。事实上 IxFunctor
class 本身就很无聊 –
instance IxFunctor f
与
基本相同
instance Functor (f j k)
现在,当您考虑更具体的函子 classes 时,就会变得有趣。这个 monad 实际上不在 Indexed
模块中,但我认为它最清楚地说明了这一点:
class IxPointed f => IxMonad f where
ijoin :: m j k (m k l a) -> m j l a
并排比较:
(>>>) :: (j->k) -> (k->l) -> j->l
ijoin :: m j k (m k l a) -> m j l a
join :: m (m a) -> m a
所以我们所做的是,在加入“容器层”的同时,我们组合 态射。
最明显的例子是IxState
。回想一下标准状态 monad
newtype State s a = State { runState :: s -> (a, s) }
当用作 monad 时,它简单地构成了函数的 s -> s
方面:
join (State f) = State $ \s -> let (State f', s') = f s in f' s'
所以你先通过 f
线程状态,然后通过 f'
。好吧,我们真的没有理由需要所有州都具有相同的类型,对吗?毕竟,中间状态只是传递给下一个动作。这是索引状态 monad,
newtype IxState i j a = IxState { runIxState :: i -> (a, j) }
它就是这样做的:
ijoin (IxState f) = IxState $ \s -> let (IxState f', s') = f s in f' s'
在 Haskell 中研究函子时,我想出了 Functor.Indexed type of functor. This functor defines an operation called imap
. I didn't understood its definition and imap
signature: imap :: (a -> b) -> f j k a -> f j k b
. I tried to find it s formal definition and found only this: http://ncatlab.org/nlab/show/indexed+functor 。但它真的对我一点帮助都没有。那么有人可以用更简单的话来澄清这种函子吗?我应该在什么情况下使用它?谢谢。
用 spacesuitburritoesque 措辞来说,索引仿函数是“一个还包含映射的容器”。 IE。一个值 f j k a
将“包含”某种态射 j -> k
(不一定是函数,可以是更一般的箭头) 以及 类型的值=20=].
对于那些 a
值,容器显然是一个函子。事实上 IxFunctor
class 本身就很无聊 –
instance IxFunctor f
与
基本相同instance Functor (f j k)
现在,当您考虑更具体的函子 classes 时,就会变得有趣。这个 monad 实际上不在 Indexed
模块中,但我认为它最清楚地说明了这一点:
class IxPointed f => IxMonad f where
ijoin :: m j k (m k l a) -> m j l a
并排比较:
(>>>) :: (j->k) -> (k->l) -> j->l
ijoin :: m j k (m k l a) -> m j l a
join :: m (m a) -> m a
所以我们所做的是,在加入“容器层”的同时,我们组合 态射。
最明显的例子是IxState
。回想一下标准状态 monad
newtype State s a = State { runState :: s -> (a, s) }
当用作 monad 时,它简单地构成了函数的 s -> s
方面:
join (State f) = State $ \s -> let (State f', s') = f s in f' s'
所以你先通过 f
线程状态,然后通过 f'
。好吧,我们真的没有理由需要所有州都具有相同的类型,对吗?毕竟,中间状态只是传递给下一个动作。这是索引状态 monad,
newtype IxState i j a = IxState { runIxState :: i -> (a, j) }
它就是这样做的:
ijoin (IxState f) = IxState $ \s -> let (IxState f', s') = f s in f' s'