作者热门文章
- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我想了解ocaml中迭代器、枚举和序列的区别
enumeration:
type 'a t = {
mutable count : unit -> int; (** Return the number of remaining elements in the enumeration. *)
mutable next : unit -> 'a; (** Return the next element of the enumeration or raise [No_more_elements].*)
mutable clone : unit -> 'a t;(** Return a copy of the enumeration. *)
mutable fast : bool; (** [true] if [count] can be done without reading all elements, [false] otherwise.*)
}
sequence:
type 'a node =
| Nil
| Cons of 'a * 'a t
and 'a t = unit -> 'a node
我对迭代器一无所知
最佳答案
BatEnum
(你称之为“枚举”,但让我们使用模块名称代替)或多或少与生成器同构,这通常被称为基于拉动:
generator : unit -> 'a option
这意味着“每次你调用generator()
,我都会从集合中给你一个新的元素,直到没有更多的元素并返回None
” .请注意,这意味着之前的元素不可访问。这种行为被称为“破坏性”。
这类似于 gen图书馆。这样的迭代器从根本上来说是非常必要的(它们通过维护当前状态来工作)。
基于拉的方法不一定具有破坏性,这就是 Seq
的地方类型适合。它是一个类似列表的结构,除了每个节点都隐藏在闭包后面。它类似于惰性列表,但不保证持久性。通过对它们进行模式匹配,您可以像处理列表一样操作这些序列。
type 'a node =
| Nil
| Cons of 'a * 'a seq
and 'a seq = unit -> 'a node
迭代器,例如 sequence ,也称为“基于推送”,其类型类似于您在许多数据结构中找到的 iter
函数:
iterator : ('a -> unit) -> unit
这意味着“迭代器 f
将把 f
函数应用于集合中的所有元素”。
拉式方法和推式方法之间的一个关键区别是它们的表现力。假设您有两个生成器,gen1
和 gen2
,添加它们很容易:
let add gen1 gen2 =
let gen () =
match gen1(), gen2() with
| Some v1, Some v2 -> Some (v1+v2)
| _ -> None
in
gen
但是,您无法使用大多数基于推送的方法(例如 sequence
)真正编写这样的函数,因为您无法完全控制迭代。
另一方面,基于推送的迭代器通常更容易定义并且速度更快。
从 OCaml 4.07 开始,Seq
在标准库中可用。有一个seq
您现在可以使用的兼容包,以及相关 oseq 中的大型组合器库图书馆。Seq
快速、富有表现力且相当易于使用,因此我推荐使用它。
关于ocaml - 迭代器、枚举和序列之间的区别,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49922197/
我是一名优秀的程序员,十分优秀!