Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

is begin..end in OCaml syntactic sugar?

Tags:

syntax

ocaml

Looking at an unofficial OCaml grammar in this site the only production where begin appears is:

Expression ::= begin Expression end

and a little further down one sees:

Expression ::= (   Expression  [:Type]   )

That, together with some offhand replacements of begin / end with ( / ) in some trivial code (which didn't affect correctness) might seem to suggest that the begin end keywords are just syntactic sugar. Or am I missing something?

like image 678
Marcus Junius Brutus Avatar asked Mar 28 '12 18:03

Marcus Junius Brutus


2 Answers

“Syntactic sugar” suggests a simple but not trivial translation to other constructs. begin .. end is not syntactic sugar, it is redundant with ( .. ), because it does exactly the same thing.

If you are interested, the intention was that programmers can use begin .. end to enclose an imperative expression, executed for its side-effects, and ( .. ) for an expression with a non-unit value. But the compiler does not enforce that, the designers of the language just thought it would look nicer if they were used in this fashion, that's all.

like image 194
Pascal Cuoq Avatar answered Dec 13 '22 19:12

Pascal Cuoq


In fact, there are several uses of parenthesis in the OCaml grammar for different grammatical rules, and not all of them can be used with begin..end. Parenthesis and begin..end can be used as semantics-free expression delimiters for disambiguation purpose (as you said, expr ::= '(' expr ')'). () also represents the constant of type unit and, as a pun, begin end is also allowed there -- but this last one is not specified in the manual, only consistently supported by the implementation.

But parentheses can also be used

  • to delimit patterns: function (_::_)::_ -> ...
  • as syntactic sugar for Array.get and Array.set: t.(i) t.(i) <- e
  • for type annotations (e : t) both in expressions and patterns (this is not a special case of the disambiguating delimiters because it is not valid without parenthesis)
  • for subtyping coercions: (e :> t) and (e : s :> t)
  • to form labelled pattern compounds: fun ~(x:int) .. and fun ?(x=10) ..
  • in various related places (coercions, annotations, etc.) in the module, signature and class/objects parts of the syntax

For none of this use can begin..end used instead, so it would definitely not be valid to replace ( with begin and ) with end systematically (while the converse is correct).

Sorry for the pedantic answer, but the question was itself quite precise. I'm not sure begin..end handling is the most elegant part of OCaml grammar (which has it lots of warts). One could wish that they really were equivalent, but then there is little point in insisting on writing begin x : int end instead of (x : int).

like image 22
gasche Avatar answered Dec 13 '22 20:12

gasche