I noticed that the following code compiles and works in VS 2013:
let f() =
do Console.WriteLine(41)
42
But when looking at the F# 3.0 specification I can't find any mention of do
being used this way. As far as I can tell, do
can have the following uses:
- As a part of loop (e.g.
while expr do expr done
), that's not the case here. Inside computation expressions, e.g.:
seq { for i in 1..2 do do Console.WriteLine(i) yield i * 2 }
That's not the case here either,
f
doesn't contain any computation expressions.Though what confuses me here is that according to the specification,
do
should be followed byin
. Thatin
should be optional due to lightweight syntax, but adding it here causes a compile error (“Unexpected token 'in' or incomplete expression”).Statement inside a module or class. This is also not the case here, the
do
is inside a function, not inside a module or a class.
I also noticed that with #light "off"
, the code doesn't compile (“Unexpected keyword 'do' in binding”), but I didn't find anything that would explain this in the section on lightweight syntax either.
Based on all this, I would assume that using do
inside a function this way should not compile, but it does. Did I miss something in the specification? Or is this actually a bug in the compiler or in the specification?
do
binding. I couldn't find it in the spec, but it's documented on MSDN. – Cullindo
inside a module. “Use a do binding when you want to execute code independently of a function” – Preservativemodule Foo = do ()
doesn't compile either with#light "off"
. – Lennondo
bindings (in a module or class constructor). Otherdo
bindings could appear anywhere aunit
expression is allowed. – Cullindo
bindings in functions. – Preservativemodule Foo = begin do () end
does compile with#light "off"
. – Preservative