如何进行模式匹配,执行函数然后对执行的函数进行模式匹配以执行另一个函数

时间:2014-12-11 07:57:35

标签: recursion ocaml

我想编写一个将数组中的元素从一个地方复制到另一个地方的函数。 copy_obj就是这样做的功能。现在我给出了一个指针列表,表示我需要复制的元素的位置,因此我需要在列表中的每个元素上应用函数copy_obj,以及我应该开始复制的空闲位置的地址。在我的代码中,它是f。

考虑到函数copy_obj返回一对地址,一个是free的更新值,我需要用来递归调用列表中其他元素的函数。

下面是我编写的代码,它编译但是我在| h::tl -> copy_obj f h发出警告说这个"表达式应该有类型单位"

我该怎么做才能安排?

let rec funct f myList =
  match myList with
  | [] -> f
  | h::tl-> 
      copy_obj f h;
      match (copy_obj f h) with
      | (free_n,addr_n) -> funct free_n tl   

1 个答案:

答案 0 :(得分:4)

你好像是另一个写着Copy GC的学生。 : - )

表达式e1; e2将按顺序执行e1e2,通常e1的返回类型应为unit,这意味着“返回没什么特别的”。如果e1是一个类型不是unit的表达式,则OCaml编译器会发出警告:“表达式应该具有类型单位”,因为您可以通过e1计算有意义的内容但是你扔掉它。它有时是可能的错误的良好迹象。

在您的情况下,copy_obj f h会返回一个元组,可能是(int * int),而不是unit。因此你得到了警告。如果您确实可以放弃计算结果,则必须写ignore (copy_obj f h),其中ignore : 'a -> unit

你曾两次致电copy_obj f h,这看起来很奇怪。如果没有函数的定义,我们无法100%确定,但我猜您不需要第一次调用:

let rec funct f myList =
  match myList with
  | [] -> f
  | h::tl-> 
      match copy_obj f h with
      | (free_n,addr_n) -> funct free_n tl   

如果您正在实施复制GC,并且如果copy_obj将对象h复制到使用副作用的可用位置,则在此处调用该函数两次将h存储两次。对于GC算法来说,这将是一个严重的错误。警告实际上试图帮助你在这一点!

还有一件事。 match并不是解构价值的唯一方法。 let也可以提取元组的元素。通常我们这样写:

let rec funct f myList =
  match myList with
  | [] -> f
  | h::tl-> 
      let (free_n, addr_n) = copy_obj f h in
      funct free_n tl   

或者你可以简单地写funct (fst (copy_obj f h)) tl