显然,每个人Arrow
都是一个Strong
profunctor。确实^>>
和>>^
对应于lmap
和rmap
。和和first'
和second'
一样。同样每一个也是。first
second
ArrowChoice
Choice
与箭头相比,profunctors缺乏的是组合它们的能力。如果我们添加合成,我们会得到一个箭头吗?换句话说,如果一个(强)profunctor 也是一个category,它是否已经是一个箭头?如果没有,缺少什么?
@haoformayor 的回答(和参考论文)是对基本类别理论的一个很好的洞察——幺半群类别相当漂亮!- 但我认为一些代码向您展示如何将 aArrow
转换为 a Strong Category
,反之亦然,因为它们出现在各自的库中可能会成为一个有用的附录。
import Control.Arrow
import Control.Category
import Data.Profunctor
import Data.Profunctor.Strong
import Prelude hiding (id, (.))
单程...
newtype WrapP p a b = WrapP { unwrapP :: p a b }
instance Category p => Category (WrapP p) where
id = WrapP id
WrapP p . WrapP q = WrapP (p . q)
instance (Category p, Strong p) => Arrow (WrapP p) where
first = WrapP . first' . unwrapP
second = WrapP . second' . unwrapP
-- NB. the first usage of id comes from (->)'s Category instance (id :: a -> a)
-- but the second uses p's instance (id :: p a a)
arr f = WrapP $ dimap f id id
……还有其他……
newtype WrapA p a b = WrapA { unwrapA :: p a b }
instance Arrow p => Profunctor (WrapA p) where
dimap f g p = WrapA $ arr f >>> unwrapA p >>> arr g
instance Arrow p => Strong (WrapA p) where
first' = WrapA . first . unwrapA
second' = WrapA . second . unwrapA