Lean 函数式编程

5. 函子、应用函子和单子🔗

FunctorMonad 都描述了那些仍在等待类型参数的类型的操作。一种理解它们的方式是,Functor 描述了容器,其中容器内的数据可以被转换,而 Monad 描述了具有副作用的程序编码。然而,这种理解是不完整的。毕竟,Option 同时拥有 FunctorMonad 的实例,并且同时代表着一个可选值 一个可能无法返回值的计算。

从数据结构的角度来看,Option 有点像一个可为空的类型,或者像一个最多可以包含一个条目的列表。从控制结构的角度来看,Option 代表着一种可能会提前终止而没有结果的计算。通常,使用 Functor 实例的程序最容易被理解为将 Option 用作数据结构,而使用 Monad 实例的程序则更容易被理解为将 Option 用于支持早期失败,但熟练地掌握这两种视角对于精通函数式编程至关重要。

函子 (Functor) 和 单子 (Monad) 之间有一个更深层次的关系。事实证明,每个单子都是一个函子。换句话说,单子抽象 (Monad Abstraction) 比函子抽象 (Functor Abstraction) 更强大,因为不是每个函子都是单子。此外,还有一个额外的中间抽象,被称为应用函子 (Applicative Functors),它有足够的能力来编写许多有趣的程序,而且还适用于那些无法使用 Monad 接口的库。类型类 Applicative 提供了应用函子的可重载操作。每个单子都是一个应用函子,而每个应用函子也都是一个函子,但反之则不成立。

  1. 5.1. 结构体和继承
  2. 5.2. 应用函子
  3. 5.3. 应用函子的契约
  4. 5.4. 选择子
  5. 5.5. 宇宙
  6. 5.6. 完整定义
  7. 5.7. 总结