Haskell语言学习笔记(35)Contravariant
来源:互联网 发布:恋舞刷m币软件 编辑:程序博客网 时间:2024/05/16 05:48
contravariant 模块
contravariant 模块需要安装
$ cabal install contravariantcontravariant-1.4Prelude> :m +Data.Functor.ContravariantPrelude Data.Functor.Contravariant>
Contravariant Functor(逆变函子)
class Contravariant f where contramap :: (a -> b) -> f b -> f a (>$) :: b -> f b -> f a (>$) = contramap . const
Functor(函子)类型类是协变的,因此它可以被看做 Covariant Functor (协变函子)的简写。
Functor是协变,是因为它改变的是输出端,相对于函数定义来说是正向的(positive)。
与此相对,Contravariant 类型类是逆变的,它是 Contravariant Functor (逆变函子)的简写。
Contravariant是逆变,是因为它改变的是输入端,相对于函数定义来说是反向的(negative)。
Contravariant 的法则
1. contramap id = id2. contramap f . contramap g = contramap (g . f)
Predicate(谓词)是个Contravariant
newtype Predicate a = Predicate { getPredicate :: a -> Bool }instance Contravariant Predicate where contramap f g = Predicate $ getPredicate g . f
Predicate(谓词 )类型封装了一个 a -> Bool 类型的函数。
证明 Predicate 符合 Contravariant 的法则1. contramap id = idcontramap id p= Predicate $ getPredicate p . id= Predicate $ getPredicate p= p = id p2. contramap f . contramap g = contramap (g . f)(contramap f . contramap g) p= contramap f (contramap g p)= contramap f (Predicate $ getPredicate p . g)= Predicate $ getPredicate (Predicate $ getPredicate p . g) . f= Predicate $ (getPredicate p . g) . f= Predicate $ getPredicate p . g . fcontramap (g . f) p= Predicate $ getPredicate p . (g . f)= Predicate $ getPredicate p . g . f
import Data.Functor.ContravariantgreaterThanThree :: Predicate IntgreaterThanThree = Predicate (> 3)lengthGTThree :: Predicate [a]lengthGTThree = contramap length greaterThanThreeenglishGTThree :: Predicate IntenglishGTThree = contramap english lengthGTThreeenglish :: Int -> Stringenglish 1 = "one"english 2 = "two"english 3 = "three"english 4 = "four"english 5 = "five"english 6 = "six"english 7 = "seven"english 8 = "eight"english 9 = "nine"english 10 = "ten"main :: IO ()main = print $ filter (getPredicate englishGTThree) [1..10]-- [3,4,5,7,8,9]
Comparison a 是个Contravariant
newtype Comparison a = Comparison { getComparison :: a -> a -> Ordering }instance Contravariant Comparison where contramap f g = Comparison $ on (getComparison g) f
Comparison a(同类比较)类型封装了一个 a -> a -> Ordering 类型的函数(比如 compare 函数)。
on :: (b -> b -> c) -> (a -> b) -> a -> a -> c(*) `on` f = \x y -> f x * f y证明 Comparison a 符合 Contravariant 的法则1. contramap id = idcontramap id c= Comparison $ on (getComparison c) id= Comparison $ \x y -> (getComparison c) (id x) (id y) = Comparison $ \x y -> (getComparison c) x y= Comparison $ getComparison c= c = id c2. contramap f . contramap g = contramap (g . f)(contramap f . contramap g) c= contramap f (contramap g c)= contramap f (Comparison $ on (getComparison c) g)= contramap f (Comparison $ on (getComparison c) g)= Comparison $ on (getComparison (Comparison $ on (getComparison c) g)) f= Comparison $ on (on (getComparison c) g) f= Comparison $ on (\x y -> (getComparison c) (g x) (g y)) f= Comparison $ \x y -> (\x y -> (getComparison c) (g x) (g y)) (f x) (f y)= Comparison $ \x y -> (getComparison c) (g (f x)) (g (f y))contramap (g . f) c= Comparison $ on (getPredicate c) (g . f)= Comparison $ \x y (getPredicate c) ((g . f) x) ((g . f) y)= Comparison $ \x y -> (getComparison c) (g (f x)) (g (f y))
Prelude Data.Functor.Contravariant Data.List> sortBy (getComparison $ contramap length $ Comparison compare) ["Groovy","Java","Scala"]["Java","Scala","Groovy"]Prelude Data.List Data.Function> sortBy (compare `on` length) ["Groovy","Java","Scala"]["Java","Scala","Groovy"]Prelude Data.List> sortOn length ["Groovy","Java","Scala"]["Java","Scala","Groovy"]
Const a 是个Contravariant
newtype Const a b = Const { getConst :: a }instance Contravariant (Const a) where contramap _ (Const a) = Const a
Const a b 封装了一个值 a。
证明 Const a 符合 Contravariant 的法则1. contramap id = idcontramap id (Const a) = Const a = id (Const a)2. contramap f . contramap g = contramap (g . f)(contramap f . contramap g) (Const a)= contramap f (contramap g (Const a))= contramap f (Const a)= Const a= contramap (g . f) (Const a)
正向与反向
a -- positive positiona -> Bool -- negative position(a -> Bool) -> Bool -- positive position((a -> Bool) -> Bool) -> Bool -- negative positiona -> Bool -> Bool = a -> (Bool -> Bool) -- negative position
参考链接
What is a contravariant functor?
阅读全文
0 0
- Haskell语言学习笔记(35)Contravariant
- Haskell语言学习笔记(1)
- Haskell语言学习笔记(2)
- Haskell语言学习笔记(4)Functor
- Haskell语言学习笔记(5)Applicative
- Haskell语言学习笔记(6)Monad
- Haskell语言学习笔记(8)Monoid
- Haskell语言学习笔记(14)Foldable
- Haskell语言学习笔记(16)Alternative
- Haskell语言学习笔记(17)MonadPlus
- Haskell语言学习笔记(18)Traversable
- Haskell语言学习笔记(21)Array
- Haskell语言学习笔记(22)MaybeT
- Haskell语言学习笔记(29)CPS
- Haskell语言学习笔记(31)ListT
- Haskell语言学习笔记(39)Category
- Haskell语言学习笔记(42)Bifunctor
- Haskell语言学习笔记(45)Profunctor
- 【BZOJ4944】【NOI2017】泳池 概率DP 常系数线性递推 特征多项式 多项式取模
- 指令的交互与ajax异步出现的问题
- DB2获取第一天
- python基础-进程池、submit同异步调用、shutdown参数、ProcessPoolExecutor进程池、进程池ftp
- BZOJ 1143 祭祀river【二分图之偏序集的最大反链】
- Haskell语言学习笔记(35)Contravariant
- Spring之IOC的注入方式总结
- springboot发布成jar并支持jsp
- xUtils框架的介绍(一)
- Android内存管理机制
- 数据结构-图-深度优先遍历邻接矩阵(1)
- ListView与GridView异步加载图片
- 快速的搭建JFinal的ORM框架示例
- Android 生成so文件加载时NoSuchMethodException