Core中的List.sum,不了解容器

时间:2019-05-04 21:12:21

标签: module ocaml ocaml-core

我正试图从简街核心了解List.sum。我得到了它来处理一个简单的整数列表,但不了解Core容器的概念,而是想简洁地找到api文档。这是一些有效的代码:

#require "core";;
open Core;;
List.sum (module Int) [1;2;3] ~f:ident;;
- : int = 6


#show List.sum;;

val sum :
  (module Base__.Container_intf.Summable with type t = 'sum) ->
  'a list -> f:('a -> 'sum) -> 'sum

为什么必须使用module Int和身份函数。 [1;2;3]已经提供了一种int list。关于Core背后的设计思想是否有很好的信息?

1 个答案:

答案 0 :(得分:3)

该模块提供了将有关值求和的方法。 f提供了从列表中的元素类型到要求和的元素类型的转换功能。

如果您只想对列表中的整数求和,则所需的求和函数位于Int模块中(因此我们需要module Int),而转换函数仅为{{ 1}}(因为我们根本不需要转换值)。

但是,如果要获取整数总和,但要从代表整数的字符串列表开始,该怎么办?这样我们就可以

ident

ie,如果我们想使用utop # List.sum (module Int) ["1";"2";"3";"4"];; - : f:(string -> int) -> int = <fun> 对字符串列表求和,那么我们首先需要一个将module Int类型的值转换为{{ 1}}。因此:

string

这很冗长,但是它给了我们很大的灵活性!想象一下,尝试对记录中的特定字段使用不同的交换运算求和。

但是,这不是对OCaml中的整数列表求和的惯用方式。 intutop # List.sum (module Int) ["1";"2";"3";"4"] ~f:Int.of_string;; - : int = 10 模块“继承”的特定功能,因为它满足List.sum的库设计中使用的容器接口(它提供了{{1的基本功能}}。之所以使用此函数相对复杂,是因为它是对代数结构(在这种情况下,是对元素集合的高度泛化设计的结果,这些元素集合可以转换为在其上定义了可交换运算的元素)

对于平凡的整数求和,OCamler仅使用简单的折叠:

List

https://dev.realworldocaml.org/是寻找Base背后的设计决策的一些好地方。另一个好的资源是Janestreet tech blog。您也可以在https://github.com/janestreet/base

中查阅Core回购(https://discuss.ocaml.org/)或发布问题以询问有关设计原理的更多详细信息。

Janestreet的图书馆对新人来说一直是不透明的,但是它们却变得越来越好,社区将很乐意帮助您学习。

文档简洁明了,表达力强。特别是,它往往依赖于类型来承担很多重量,这意味着代码在很大程度上是自我记录的。学习一些好的类型需要一些练习,但是,值得付出努力,imo,并有自己的收获!