Distributive

class Functor g => Distributive g where
distribute :: Functor f => f (g a) -> g (f a)
distribute = collect id collect :: Functor f => (a -> g b) -> f a -> g (f b)
collect f = distribute . fmap f distributeM :: Monad m => m (g a) -> g (m a)
distributeM = fmap unwrapMonad . distribute . WrapMonad collectM :: Monad m => (a -> g b) -> m a -> g (m b)
collectM f = distributeM . liftM f cotraverse :: (Distributive g, Functor f) => (f a -> b) -> f (g a) -> g b
cotraverse f = fmap f . distribute comapM :: (Distributive g, Monad m) => (m a -> b) -> m (g a) -> g b
comapM f = fmap f . distributeM

Distributive 是个类型类。功能上与 Traversable 类型类呈现对偶(dual)关系。

Traversable 类型将一个函数应用到多个数值,而

Distributive 类型将一个数值应用到多个函数。

((->)e) 是个 Distributive

instance Distributive ((->)e) where
distribute a e = fmap ($e) a
collect f q e = fmap (flip f e) q

Sum 是个 Distributive

instance Distributive Monoid.Sum where
collect = coerce (fmap :: (a -> b) -> f a -> f b)
:: forall f a b . Functor f
=> (a -> Monoid.Sum b) -> f a -> Monoid.Sum (f b)
distribute = Monoid.Sum . fmap Monoid.getSum

应用 Distributive

Prelude Data.Distributive> distribute [(+1),(+2)] 1
[2,3]
Prelude Data.Distributive> collect (^) [1,2] 3
[1,8]
Prelude Data.Distributive> cotraverse sum [(+1),(*2)] 3
10
Prelude Data.Distributive> comapM product [(+1),(*2)] 3
24
Prelude Data.Distributive Data.Monoid> distribute [Sum 1, Sum 2]
Sum {getSum = [1,2]}
Prelude Data.Distributive Data.Monoid> collect (\x->Sum[x]) [3,4]
Sum {getSum = [[3],[4]]}

手动计算

distribute [(+1),(+2)] 1
= fmap ($1) [(+1),(+2)]
= [1+1,1+2] = [2,3]
collect (^) [1,2] 3
= fmap (flip (^) 3) [1,2]
= fmap (^3) [1,2]
= [1^3,2^3] = [1,8]
cotraverse sum [(+1),(*2)] 3
= (fmap sum . distribute) [(+1),(*2)] 3
= sum $ distribute [(+1),(*2)] 3
= sum [4, 6] = 10 这里
(fmap f . g) x y
= (f . g x) y
= f $ g x y

最新文章

  1. linux下重启apache
  2. ギリギリ eye (优先队列)
  3. 判断一个点是否在多边形内部,射线法思路,C#实现
  4. android加载大图片到内存
  5. D3D9 GPU Hacks (转载)
  6. 转载 uboot 命令
  7. 表单Ext.form.FormPanel(转)
  8. jQuery 删除或是清空某个HTML元素示例
  9. GridView官方教程及示例
  10. android Xml生成一条细线,以及获取屏幕宽度和高度
  11. Minor GC、Major GC和Full GC之间的区别(转)
  12. [置顶] 页面缓存,cache,设置缓存过期时间,OutputCache
  13. 设计模式学习--Factory Method
  14. Delphi xe7并行编程快速入门(转)
  15. iOS 原生的 UIButton 点击事件是不允许带多参数的,唯一的一个参数就是默认UIButton本身 那么我们该怎么实现传递多个参数的点击事件呢?
  16. Mysql之左连接右连接内连接——示例 (转)
  17. Codeforces Round #395 (Div. 2)(未完)
  18. qtchooser
  19. Python IDLE配置清屏快捷键(Ctrl+L)
  20. redis做session会话共享

热门文章

  1. centos7 安装Zabbix3.0
  2. bzoj 3277 串 && bzoj 3473 字符串 && bzoj 2780 [Spoj]8093 Sevenk Love Oimaster——广义后缀自动机
  3. JZ2440 裸机驱动 第9章 中断体系结构
  4. python 异常类型----后期需理解调整
  5. CentOS启动网络提示connect: Network is unreachable(配置静态路由)
  6. framework4.0 IIS7下urlrewriter设置问题
  7. java接口定义和作用
  8. PAT-甲级刷题笔记和总结
  9. 详解UE4静态库与动态库的导入与使用
  10. python protobuf序列化repeated运用