我,我在ocaml中有这个简单的程序
type tree = Node of string * exp * tree * tree | Empty
and exp = Etree of tree | EInt of int | List of (string*exp);;
let rec evalNode.......
and rec eval (e:exp) =
(match e with
| EInt _ -> e
| Etree(tree) -> (match tree with
| Empty -> []
| Node(s,i,t1,t2) -> (evalNode (tree)) )
)
evalNode:tree - > (string * exp)list = fun
eval:exp - > exp = fun
但是返回此错误但是我没有理解这意味着什么,网络中没有太多关于ocaml的信息:
此表达式具有type(string *'a)列表, 但是与exp。类型一起使用。
Etree里面有一个类型的Node,所以是类型树,所以我可以用这个值调用evalNode,因为它需要一个树类型
evalNode返回一个(string * exp)列表但是是exp,所以eval可以返回这个
答案 0 :(得分:1)
Ocaml中的任何表达式都必须返回单个类型。因此,例如,您不能编写类似if a>b then "a" else 7
的内容,因为它不知道该表达式的类型是字符串还是int。
在你的eval函数中,没有意义,你做了类似的事情。当e
为EInt
时,会触发第一个匹配选项,并返回类型为e
的{{1}}。当exp
为e
时,它会触发第二个匹配选项,该选项又会调用第二个匹配语句并触发其中的第一个匹配选项,返回Etree(Empty)
,这是一个具有类型的列表[]
(意思是未知类型的列表)。如果'a list
是e
,则会触发第二个匹配语句中的第二个匹配选项,并返回Etree(Node(s,i,t1,t2))
,我们根据您所写的内容返回evalnode(tree)
类型(string * exp) list
因此,内部匹配本身很好,因为它可以统一具有特定列表的通用列表。但是组合外部匹配是有问题的,因为第一种情况返回exp
而第二种情况返回(string * exp) list
,因此它不知道表达式应该具有什么类型。我不确定为什么错误会显示(string * 'a) list
而不是(string * exp) list
,但我怀疑你可以解决问题而无需解决问题。
我还要注意您有一个构造函数List of (string*exp)
,其子类型不是列表。您可能希望这是List of (string*exp) list
,然后让您的内部匹配返回List([])
和List(evalNode(tree))
,但这只是猜测。
答案 1 :(得分:0)
evalNode返回(string * exp)列表,但是是exp
这是您的错误:string * exp
列表不是exp
;编译器无法猜测您是否打算应用构造函数List
从此列表构建exp
(如果List
的正确定义恰好是List of (string * exp) list
)。