Array.length在OCaml中的实现



我想了解Array.length是如何实现的。我设法用Array.fold_left:写了它

let length a = Array.fold_left (fun x _ -> x + 1) 0 a

然而,在标准库中,fold_left使用length,所以这不可能。对于length,stdlib中只有这一行我不理解:

external length : 'a array -> int = "%array_length"

如何在不使用fold_left的情况下编写length

编辑:

我试着用模式匹配来做,但它并不是详尽无遗的,我如何才能使匹配更精确?(目的是删除最后一个元素,当只剩下一个元素时返回i+1(

let length a = 
let rec aux arr i = 
match arr with
| [|h|] -> i+1
| [|h;t|] -> aux [|h|] (i+1)
in aux a 0;;

数组类型是一个基元类型,类似于int类型。许多基元函数在这些基元类型上的实现是用C函数或编译器基元完成的。

Array.length函数属于编译器基元类别,在标准库中由定义

external length : 'a array -> int = "%array_length"

这里,该声明将值length绑定到类型为'a array -> int的编译器原语%array_length(编译器原语名称以%符号开头(。在从源代码到本机代码或字节码的转换过程中,编译器将这种编译器原语转换为较低级别的实现。

换句话说,您自己无法以有效的方式重新实现Array.length或数组类型,因为该类型是编译器本身定义的基本构建块。

对于length,stdlib中只有一行我不理解:

external关键字表示此函数是用C实现的,"%array_length"是命名此函数的C符号。OCaml运行时是用C语言实现的,一些类型(如数组(是内置的(也称为基元(。

参见第20章:用OCaml接口C中的实现原语示例

我试着用模式匹配来做这件事,但它并不是详尽无遗的,我如何才能使匹配更精确

请注意,OCaml告诉您哪种模式不匹配:

Here is an example of a case that is not matched:
[|  |]

所以你也必须考虑空向量。

相关内容

  • 没有找到相关文章

最新更新