如何返回具有更新值的新类型

时间:2015-04-29 04:51:47

标签: functional-programming ocaml

如果我想更改列表中的值,我将返回一个包含新值的新列表,而不是更改旧列表中的值。

现在我有四种类型。我需要更新varEnd中的值位置,而不是更改值,我需要返回一个具有更新值的新类型

type varEnd = {
v: ctype;
k: varkind;
l: location; 
}
;;

type varStart = {
ct: ctype;
sy: sTable;
n: int;
stm: stmt list;
e: expr
}

and sEntry = Var of varEnd | Fun of varStart
and sTable = (string * sEntry) list
type environment = sTable list;;

(a function where environment is the only parameter i can use) 
let allocateMem (env:environment) : environment = 

我尝试使用List.iter,但它直接更改了值,哪种类型也不可变。我认为List.fold将是一个更好的选择。

我遇到的最大问题是有四种不同的类型。

1 个答案:

答案 0 :(得分:0)

我认为您说您知道如何通过构建新列表来更改列表元素。

现在,您希望对环境执行此操作,而环境是一个非常复杂的事项列表。但这没有任何区别,更改列表的方式是相同的。唯一的区别是重置价值将是一件复杂的事情。

当你说你有四种类型时,我不知道你的意思。我看到这里列出的类型超过四种。但另一方面,环境似乎包含两种不同类型的东西。

也许(但可能不是)你说你不知道改变记录的四个字段之一的好方法,而其他字段保持不变。这是一个很好的答案。假设x是varEnd类型的东西。然后你可以说:

{ x with l = loc }

事实上,如果您不知道如何通过创建新列表来修改列表元素,那么首先要弄清楚这一点。你可以用折叠来做,但事实上你也可以用List.map来做,这有点简单。您无法使用List.iter

执行此操作

<强>更新

假设我们有这样的记录类型:

type r = { a: int; b: float; }

这是一个功能r list list,并将b字段为0的记录的a字段添加1.0。

let incr_ll rll =
    let f r = if r.a = 0 then { r with b = r.b +. 1.0 } else r in
    List.map (List.map f) rll

此功能的类型为r list list -> r list list