Functional programming OCaml中let-rec的局限性

Functional programming OCaml中let-rec的局限性,functional-programming,ocaml,Functional Programming,Ocaml,我最近在学习OCaml,遇到了这样一个问题: OCaml限制了它可以放在let rec右侧的内容,比如这个 let memo_rec f_norec = let rec f = memoize (fun x -> f_norec f x) in f;; Error: This kind of expression is not allowed as right-hand side of `let rec' 其中,memoize是一个函数,它接受一个函数并将其转换为具有哈希表的记忆版本。

我最近在学习OCaml,遇到了这样一个问题:

OCaml限制了它可以放在let rec右侧的内容,比如这个

let memo_rec f_norec =
let rec f = memoize (fun x -> f_norec f x) in
f;; 
Error: This kind of expression is not allowed as right-hand side of `let rec'

其中,memoize是一个函数,它接受一个函数并将其转换为具有哈希表的记忆版本。很明显,OCaml对“let rec”右侧的结构的使用有一些限制,但我真的不明白,有人能解释一下吗?

手册的第1部分描述了允许由
let rec
绑定的表达式类型。具体而言,不允许使用包含
let rec
定义名称的函数应用程序

粗略总结(摘自该链接):

非正式地说,接受定义的类由定义名称仅出现在函数体内部或作为数据构造函数的参数的定义组成


您可以使用打结技术来定义记忆固定点。例如,请参见这两个等效定义:

let fix_memo f =
  let rec g = {contents = fixpoint}
  and fixpoint x = f !g x in
  g := memoize !g;
  !g

let fix_memo f =
  let g = ref (fun _ -> assert false) in
  g := memoize (fun x -> f !g x);
  !g
或者使用Alain提醒的
lazy

let fix_memo f =
  let rec fix = lazy (memoize (fun x -> f (Lazy.force fix) x)) in
  Lazy.force fix