我正在用一些简单的命令在 OCaml 中编写一个交互式计算器。用户应该能够定义自己的简单函数(数学函数),例如
let f(x) = x
let g(x) = 2*f(x)
现在,函数应该像函数式语言一样处理,这意味着它们应该记住它们的创建时间环境。这意味着,对于一个函数,我必须保持其环境的闭包,即函数和变量。
我将当前定义的函数保存在一个像(functions_present_at_the_time_of_creation, variables_present_at_the_time_of_creation, function_name, function_argument_names, function_formula)
. 当我尝试将一个新函数添加到函数列表中时(假设它当前未定义并且我不必覆盖任何内容),我反复迭代到函数列表的末尾并希望添加一个新的元组。
问题是,假设我当前的函数列表是类型(a*b*c*d*e) list
,当我尝试将一个带有自身的元组添加到它的末尾时,它会将其类型更改为((a*b*c*d*e) list*f*g*h*i) list
. 我能做些什么才能执行这样的列表添加到自身,封装在一个元组中?
这是我在尝试找到解决此问题的方法时编写的一些简单的 SSCCE。
let rec add_to_end list list_copy dummy = match list with
| [] -> [(list_copy, dummy)]
| h::t -> h::(add_to_end t list_copy dummy)
let add list dummy = add_to_end list list dummy
这个尝试使用列表的副本来完成。以下是在没有使用副本的情况下编写的(当然,这两个示例都不起作用):
let rec add_to_end list dummy = match list with
| [] -> [(list, dummy)]
| h::t -> h::(add_to_end t dummy)
第一个示例在尝试使用函数 add 时不起作用,但是当以这种方式(在解释器中)执行此操作时:
let l = [];;
let l = add_to_end l l 1;;
let l = add_to_end l l 2;;
let l = add_to_end l l 3;;
然后它工作正常。我会很感激任何帮助,我也可能会考虑改变设计,非常欢迎任何建议。
编辑:这是上述命令的输出:
# let l = [];;
val l : 'a list = []
# let l = add_to_end l l 1;;
val l : ('a list * int) list = [([], 1)]
# let l = add_to_end l l 2;;
val l : (('a list * int) list * int) list = [([], 1); ([([], 1)], 2)]
# let l = add_to_end l l 3;;
val l : ((('a list * int) list * int) list * int) list =
[([], 1); ([([], 1)], 2); ([([], 1); ([([], 1)], 2)], 3)]