OCaml总和类型中的int * int与(int * int) [英] int * int vs (int * int) in OCaml sum type

查看:71
本文介绍了OCaml总和类型中的int * int与(int * int)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

type foo = A of int * int | B of (int * int)

在那里int * int(int * int)有什么区别?我看到的唯一区别是模式匹配:

What is the difference between int * int and (int * int) there? The only difference I see is in pattern matching:

let test_foo = function
  | A (f, s) -> (f, s)
  | B b -> b

这只是语法糖吗?您如何选择要使用的一个?这两种形式之间在性能上有什么区别吗?

Is it just a syntactic sugar? How do you select which one to use? Is there any performance difference between these two forms?

推荐答案

是的,存在性能差异:

在内存中A (23, 42)将包含一个将其标识为A的标记以及两个整数23和42.B (23, 42)将包含一个将其标识为B的标记和一个指向包含整数的元组的指针2342.因此,在创建B时将有一个附加的内存分配,而在访问B中的各个值时将有一个附加的间接级别.因此,在实际上没有将构造函数参数用作元组的情况下,使用A会比使用B涉及更少的开销.

In memory A (23, 42) will contain a tag identifying it as an A and the two integers 23 and 42. B (23, 42) will contain a tag identifying it as a B and a pointer to a tuple containing the integers 23 and 42. So there will be one additional memory allocation when creating a B and one additional level of indirection when accessing the individual values inside a B. So in cases where you don't actually use the constructor arguments as a tuple, using A will involve less overhead than using B.

另一方面,您的test_foo函数每次使用A值调用时都会创建一个新的元组,但是当使用B值调用它时,它只会返回已存在于其中的元组.记忆.因此,对于B而言,test_foo操作要比A便宜.因此,如果将构造函数的参数用作元组,并且针对相同的值进行多次处理,则使用B会更便宜.

On the other hand your test_foo function will create a new tuple every time it is called with an A value, but when it is called with a B value it will simply return the tuple that already exists in memory. So test_foo is a cheaper operation for B than it is for A. So if you'll be using the constructor's arguments as a tuple and you will do so multiple times for the same value, using B will be cheaper.

因此,如果您打算将构造函数参数用作元组,则使用带元组的构造函数是有意义的,因为您可以使用模式匹配并使用较少的代码来获得元组,并且它将避免创建来自相同值的元组多次.在所有其他情况下,最好不使用元组,因为它涉及较少的内存分配和较少的间接寻址.

So if you're going to be using the constructor arguments as a tuple, it makes sense to use a constructor taking a tuple because you can get at the tuple using pattern matching with less code and because it will avoid having to create tuples from the same value multiple times. In all other cases not using a tuple is preferable because it involves less memory allocation and less indirection.

这篇关于OCaml总和类型中的int * int与(int * int)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆