2013-02-01 57 views
1

真正的基本问题在这里:我是Ocaml的新手,我在尝试操作列表时遇到问题。我读过http://caml.inria.fr/pub/docs/manual-ocaml/libref/List.html,很不幸我仍然感到困惑....我是功能编程新手。Ocaml操作列表

如果我有,说,下面的功能:

let stoverfl list1 list2 list3 = 
     match list1 with 
     |[]->None 
     |h::list1 -> (*what I want to do goes in here*) 

我想看看列表2和项目list3的第一要素,对它们进行比较,如果它们相等,添加的第一个元素list3到list2,否则不要修改列表。我现在并不在乎错误检查(即检查列表是否至少有一个元素,等等)。

我尝试:

h::list1 -> let cmp1 = hd list2 (*this should return the first elemnt of list2??*) 
      let cmp2 = hd list3 
      if(cmp1=cmp2) then 
       let updlist2 = concat list2 hd list3 
       let updlist3 = hd list3 
       (*pass updlist2 and updlist3 instead of list2 and list3 to next function*) 
      else 
       (*do nothing; pass list2 and list3 as normal*) 

我觉得我做的一切都是错的......任何意见,将不胜感激! 谢谢。

回答

1

你说你想添加第一个元素list3list2。当一个功能程序员说这样的话时,它意味着他们想要按照描述构建一个新列表。您实际上无法修改list2 - 列表是不可变的,并且名称永久绑定到单个值。实际上,您似乎想要构建两个新列表。其中一个在list3的前面有list2的第一个元素。另一个是list2的剩余部分(除第一个元素外)。

假设这是你的意思,并假设你不担心的名单是否为空,那么这里对这些值的一种方式:

let updlist2 = List.tl list2 in 
let updlist3 = (List.hd list2) :: list3 

这其实很接近你写的是什么。

但是,我不知道接下来要对这些值做什么。如果您想将它们传递给另一个函数,那么将let置于if的位置更为正常。作为一个例子,这里的一些代码,调用一个函数g与任何一个列表或列表的尾部,根据该列表的第一个元素:

let arg_for_g = 
    match the_list with 
    | [] -> [] (* No tail of the list *) 
    | head :: tail -> if head = 3 then tail else the_list 
in 
    g arg_for_g 

如果你把let S中if内,你需要为你的下一个函数编写两个不同的调用。这可能很好,这取决于你将如何处理你的价值观。

(作为便笺,您应该担心列表是否为空!如果您使用match声明,则可以轻松检测到该情况。)