获取Array的最小元素索引

时间:2016-10-27 12:33:28

标签: ocaml

我有一个函数,它接受一个Array和该Array中的最小值,并返回该值所在的位置。

let findMin a minimum = Array.fold_left (fun pos i -> if a[i] == minimum then i else pos) -1 (Array.range 0 (Array.length a))

当我进行类型检查时,我得到了:

Error: This expression has type 'a -> 'a array -> 'a
       but an expression was expected of type int

这部分突出显示:

(fun pos i -> if a[i] == minimum then i else pos)

那么问题是什么?

2 个答案:

答案 0 :(得分:4)

问题

字符串-1未被解析为否定文字,而是两个文字-1。所以OCaml看到你的代码如下:

Array.fold_left (fun pos i -> if a[i] == minimum then i else pos) -1 (Array.range 0 (Array.length a))

让我们通过执行以下替换来折叠表达式:

<fold> ::= Array.fold_left (fun pos i -> if a[i] == minimum then i else pos)
<range> ::= (Array.range 0 (Array.length a))

现在我们可以看到结构:

<fold> "-" "1" <range>

由于减去左关联,它首先采用一个表达式:

<fold> "-" "1"

他非常确定1int。减号是一个整数运算,到目前为止一直很好。所以类型检查器得出结论,<fold>表达式应该是你可以减去1的东西,它应该是一个int。但这是一个函数 - 所以它输出一个类型错误。

解决方案

括号-1,例如(-1),或使用前缀减去运算符~-1

答案 1 :(得分:2)

当我尝试时,Array.fold_left也会突出显示。原因很简单:-1必须括在括号中(如:(-1)),以区分一元和二元减号。其他解析者认为你想从1中减去Array.fold_left (fun pos i -> if a[i] == minimum then i else pos)

除此之外,您似乎使用非标准数组库。我的测试和答案基于标准库,所以YMMV。