Ocaml 实现多态堆栈时遇到的问题
我试图编写一个作为函子的PolishCalculator,它接收堆栈实现,遵循StackADT接口,并使用它来计算以该符号编写的表达式 因此,我开始为堆栈编写接口,它如下所示:Ocaml 实现多态堆栈时遇到的问题,ocaml,Ocaml,我试图编写一个作为函子的PolishCalculator,它接收堆栈实现,遵循StackADT接口,并使用它来计算以该符号编写的表达式 因此,我开始为堆栈编写接口,它如下所示: module type StackADT = sig type 'a stack val empty : 'a stack val pop : 'a stack -> 'a val push : 'a -> 'a stack -> unit val is_emp
module type StackADT =
sig
type 'a stack
val empty : 'a stack
val pop : 'a stack -> 'a
val push : 'a -> 'a stack -> unit
val is_empty : 'a stack -> bool
end;;
然后我尝试了一个具体的实现,如下所示:
module MyStack : StackADT =
struct
type 'a stack = {mutable c: 'a list}
exception EmptyStackException
let empty = {c = []}
let pop stack = match stack.c with
|[]-> raise EmptyStackException
|h::tl -> stack.c <- tl; h
let is_empty stack = match stack.c with
|[] -> true
|_ -> false
let push n stack = stack.c <- n::stack.c
end;;
我理解问题在于,在具体的实现中,直到我们将一个元素放入堆栈中,堆栈的类型才确定,而接口要求在调用empty之后堆栈已经被类型化,但是有什么方法可以让这件事情工作吗
感谢您在界面中编写以下内容:
val empty: 'a stack
您正在声明只有一个空堆栈,并且可以从该共享空堆栈开始构建任何堆栈
这不是实现中发生的情况,因为类型'a堆栈
是可变的
一种修复方法是用空值生成器替换此空共享值:
val empty: unit -> 'a stack
感谢您修复工作正常,我还必须将MyStack empty函数编辑为
let empty()={c=[]}
,因此基本上就像我最初编写的那样,我声明调用empty将返回对唯一空堆栈的引用?我理解对了吗?根本没有电话。所以你说StackADT类型的模块必须提供一个空值,并且模块的所有用户共享一个且只有一个可变字段。将empty定义为`+堆栈(对不起,我记不清确切的语法)也行吗。空列表是任何列表的有效起点,就像空堆栈可用于任何类型一样。可变单元格对于其内容类型是不变的,因为它们既可以读取也可以写入。如果用户A将一个函数推到空堆栈,然后用户B推一个int,那么您不希望让A尝试读回其函数并获取B的int。
val empty: unit -> 'a stack