# Constructors with several arguments

**URL:** <https://discuss.ocaml.org/t/constructors-with-several-arguments/764>\
**Category:** Learning\
**Created:** [August 24, 2017, 11:06am UTC](https://discuss.ocaml.org/t/constructors-with-several-arguments/764 "2017-08-24T11:06:53Z")\
**Posts on this page:** 5\
**Page:** 1

<div class="post-metadata">

**Author:** ![n4323](https://avatars.discourse-cdn.com/v4/letter/n/97f17d/32.png) [@n4323](https://discuss.ocaml.org/u/n4323)\
**Post date:** [August 24, 2017, 11:06am UTC](https://discuss.ocaml.org/t/constructors-with-several-arguments/764/1 "2017-08-24T11:06:53Z")

</div>

Consider this interactive session:

> utop # type a = A of int \* int;;  
> type a = A of int \* int  
> utop # type b = B of (int \* int);;  
> type b = B of (int \* int)  
> utop # A (3,4);;  
> a = A (3, 4)  
> utop # A ((3,4));;  
> a = A (3, 4)  
> utop # let t = (3,4);;  
> val t : int \* int = (3, 4)  
> utop # A t;;  
> Error: The constructor A expects 2 argument(s),  
> but is applied here to 1 argument(s)  
> utop # B (3,4);;  
> b = B (3, 4)  
> utop # B t;;  
> b = B (3, 4)

There is nothing wrong here: A has two arguments, B one. Still I find it ugly that values of type a are printed in exactly the same way as values of type b. (The types themselves are distinguishable when printed).  
Would it make sense to print variants whose only argument is a literal tuple like this: B ((3,4)) ?  
Also, A ((3,4)) is parsed as A (3,4) and is accepted, although the first form to me intuitively looks like a single argument to the constructor. Would it be cleaner to reject A ((3,4))?  
Finally, if backwards compatibility were not an issue, would the language not work just as well if only constructors with one (possibly tuple) argument were allowed at all?

---

<div class="post-metadata">

**Author:** ![Leonidas](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/leonidas/32/4039_2.png) [@Leonidas](https://discuss.ocaml.org/u/Leonidas)\
**Post date:** [August 25, 2017, 10:21am UTC](https://discuss.ocaml.org/t/constructors-with-several-arguments/764/2 "2017-08-25T10:21:22Z")

</div>

> [@n4323](#):
>
> Finally, if backwards compatibility were not an issue, would the language not work just as well if only constructors with one (possibly tuple) argument were allowed at all?

I believe it would, as you’ve shown you can always encode an n-ary constructor into an unary constructor with tuple of arguments. Since the language does not treat constructors as functions (unlike SML, which from what my casual testing does not have n-ary constructors to begin with), there are no concerns about partially applied constructors.

---

<div class="post-metadata">

**Author:** ![dra27](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/dra27/32/5294_2.png) [@dra27](https://discuss.ocaml.org/u/dra27)\
**Post date:** [August 25, 2017, 10:34am UTC](https://discuss.ocaml.org/t/constructors-with-several-arguments/764/3 "2017-08-25T10:34:27Z")

</div>

OCaml’s revised syntax addressed this point. In the revised syntax, the two declarations are:

```ocaml
type a = [A of int and int]
type b = [B of (int * int)]

```

and values have to be constructed differently:

```ocaml
value a = A 3 4
value b = B (3, 4)

```

Polymorphic variants, incidentally, are implemented as you say - they are always a tuple. There is a performance benefit to the flat representation.

---

<div class="post-metadata">

**Author:** ![anon72795300](https://avatars.discourse-cdn.com/v4/letter/a/8e7dd6/32.png) [@anon72795300](https://discuss.ocaml.org/u/anon72795300)\
**Post date:** [August 25, 2017, 11:20am UTC](https://discuss.ocaml.org/t/constructors-with-several-arguments/764/4 "2017-08-25T11:20:28Z")

</div>

Will this allow for _partial construction_? Looking at the `and` there, I guess no?

---

<div class="post-metadata">

**Author:** ![dra27](https://sea2.discourse-cdn.com/flex020/user_avatar/discuss.ocaml.org/dra27/32/5294_2.png) [@dra27](https://discuss.ocaml.org/u/dra27)\
**Post date:** [August 25, 2017, 11:36am UTC](https://discuss.ocaml.org/t/constructors-with-several-arguments/764/5 "2017-08-25T11:36:11Z")

</div>

No - it was just a revised syntax. It’s also really just a piece of OCaml history now!
