#indent "off" in F# - f#

I just started learning F#, and tried a code from the wiki:
I prefer tabs to spaces, so I change the code a bit into this:
#indent "off"
open System
open System.Windows.Forms
let form = new Form(Visible=true, TopMost=true, Text="Welcome to F#")
let label =
let temp = new Label()
let x = 3 + (4 * 5)
temp.Text <- sprintf "x = %d" x
temp
form.Controls.Add(label)
[<STAThread>]
Application.Run(form)
The output is:
Microsoft (R) F# 2.0 Compiler build
4.0.30319.1 Copyright (c) Microsoft Corporation. All Rights Reserved.
fstest2.fs(1,1): warning FS0062: This
construct is for ML compatibility.
Conside r using a file with extension
'.ml' or '.mli' instead. You can
disable this warn ing by using
'--mlcompatibility' or '--nowarn:62'.
fstest2.fs(9,2): error FS0010:
Unexpected keyword 'let' or 'use' in
expression. Expected 'in' or other
token.
fstest2.fs(13,1): error FS0597:
Successive arguments should be
separated by spac es or tupled, and
arguments involving function or method
applications should be parenthesized
fstest2.fs(9,14): error FS0374:
Invalid expression on left of
assignment
fstest2.fs(16,1): error FS0010:
Unexpected identifier in definition
Guess the error is somewhere in the let label block, but couldn't figure it out.

If you use "#indent off", then you lose all the simpler whitespace-aware syntax, and have to go back to using e.g.
#indent "off"
open System
open System.Windows.Forms
let label =
let temp = new Label() in
let x = 3 + (4 * 5) in
temp.Text <- sprintf "x = %d" x;
temp;;
let form =
let f = new Form() in
f.Controls.Add(label);
f;;
[<STAThread>]
do Application.Run(form)
with semicolons and ins and all other kinds of syntactic noise everywhere. You'll probably be happier just having your editor convert tabs to spaces (and having a smart editor that can treat spaces as though they are tabs, e.g. so that backspace can back up one tab-stop).

This topic was already discussed in this StackOverflow question. As Brian explains, turning off the "lightweight" syntax means that you'll have to write in the OCaml-compatible syntax.
I believe that in most of the cases, the syntax based on indentation is more readable (and so it is worth switching from tabs to spaces). However, the syntax with additional noise (such as in and ;;) reveals more about the structure of the language, so it may be useful to play with it briefly while learning F#.
The following example shows all the additional things that you need to write:
let add a b c =
let ab = a + b in // 'in' keyword specifies where binding (value 'ab') is valid
printfn "%d" ab; // ';' is operator for sequencing expressions
c - ab;; // ';;' is end of a function declaration
For more discussions, see also this post.

Related

How to do tuple augmentation

The following code is from chapter 5 of "F# 4.0 Design Patterns".
let a = 1,"car"
type System.Tuple<'T1,'T2> with
member t.AsString() =
sprintf "[[%A]:[%A]]" t.Item1 t.Item2
(a |> box :?> System.Tuple<int,string>).AsString()
The desired output is [[1]:["car"]]
However, a red squiggly appears under AsString(). "The field, constructor or member 'AsString' is not defined. Maybe you want one of the following: ToString"
This is a bit odd code sample - I suspect the point that this is making is that F# tuples are actually .NET tuples represented using System.Tuple - by showing that an extension to System.Tuple can be invoked on ordinary F# tuples.
I suspect the behaviour of F# has changed and it no longer allows this - it may have been that adding extensions was allowed on System.Tuple, but not on ordinary F# tuples, but the two have became more unified in the compiler.
However, you can do a very similar thing using the .NET-style extension methods:
let a = 1,"car"
[<System.Runtime.CompilerServices.ExtensionAttribute>]
type TupleExtensions =
[<System.Runtime.CompilerServices.ExtensionAttribute>]
static member AsString(t:System.Tuple<'T1,'T2>) =
sprintf "[[%A]:[%A]]" t.Item1 t.Item2
let st = (a |> box :?> System.Tuple<int,string>)
st.AsString()
This can actually be also invoked directly on an F# tuple value:
("car", 32).AsString()

Binding not exhaustive warning in SML/NJ but not in F# for same pattern

The SML/NJ code below results in a binding not exhaustive warning for "val Grove(whatTree) = glen". The F# equivalent code produces no warning. Why?
Standard ML of New Jersey (32-bit) v110.99.2 [built: Tue Sep 28 13:04:14 2021]:
datatype tree = Oak|Elem|Maple|Spruce|Fir|Pine|Willow
datatype vegetable = Carrot|Zucchini|Tomato|Cucumber|Lettuce
datatype grain = Wheat|Oat|Barley|Maize
datatype plot = Grove of tree|Garden of vegetable|Field of grain|Vacant
val glen = Grove(Oak)
val Grove(whatTree) = glen
F# 6.0.0 Warning Level 5:
type Tree = Oak|Elem|Maple|Spruce|Fir|Pine|Willow
type Vegetable = Carrot|Zucchini|Tomato|Cucumber|Lettuce
type Grain = Wheat|Oat|Barley|Maize
type Plot = Grove of Tree|Garden of Vegetable|Field of Grain|Vacant
let glen = Grove(Oak)
let Grove(whatTree) = glen
Why binding not exhaustive? The accepted answer to this related question gives me some hints about my question. The SML warning is indicating redundant code. So, I'll assume the F# compiler writers did not deem this case worthy of a warning.
This F# code let Grove(whatTree) = glen is ambiguous because it can be interpreted as value binding with deconstruction or function.
In first case syntax is
let pattern = expr
In seconds case syntax is
let name pattern-list = expr
Since F# supports shadowing, it's legal to create new function. But SML seems to have different opinion on this and decides to bind value.
In the end: code in SML and F# does different things, that's why there's no warnings
To actually perform binding, left side of let should parenthesized:
let (Grove(whatTree)) = glen
It produces warning: C:\stdin(6,5): warning FS0025: Incomplete pattern matches on this expression. For example, the value 'Field (_)' may indicate a case not covered by the pattern(s).

Why does F# Interactive behave differently than compiler with regards to immutable value definition?

In reading John Palmer's answer to What is the difference between mutable values and immutable value redefinition?, John notes that
This sort of redefinition will only work in fsi.
In working with F# Interactive (fsi) I guess I subconsciously knew it, but never paid attention to it.
Now that it is apparent, why the difference?
More specifically please explain how the internals are different between fsi and the compiler such that this occurs by design or result of differences?
If the answer can elaborate on the internal structures that hold the bindings that would be appreciated.
The semantics are consistent with the way FSI compiles interactive submissions to an FSI session: each interactive submission is compiled as module which is open to subsequent interactive submissions.
The following is close to what FSI actual does and illustrates how let binding shadowing works across interactive submissions:
FSI Submission #1: let x = 1;;
module FSI_1 =
let x = 1
open FSI_1 //FSI_1.x is now bound to 1 and available at the top level
FSI Submission #2: let x = 2;;
module FSI_2 =
let x = 2
open FSI_2 //FSI_1.x is now shadowed by FSI_2.x which is bound to 2 and available at the top level
You can see the actual details how how the dynamic FSI assembly is compiled by using reflection on the FSI_ASSEMBLY assembly within the FSI app domain. Each interactive submission is literally emitted as a module (.NET class) with the naming pattern FSI_####. FsEye uses these facts to discover the state of FSI top-level bindings: https://code.google.com/p/fseye/source/browse/tags/2.0.1/FsEye/Fsi/SessionQueries.fs#24
The key takeaway in regard to #JohnPalmer's answer is that top-level FSI definitions cannot be mutated, when they are "redefined" they are merely being shadowed. We can show this as follows:
> let x = 1;; //our original definition of x
val x : int = 1
> let f () = x;; //capture x
val f : unit -> int
> let x = 2;; //shadow our original definition of x
val x : int = 2
> f();; //returns the original x value, which is still 1 rather than 2
val it : int = 1

F# Code Execution Order

another noob question regarding F#.
If I have the following code...
let ExeC =
printfn "c"
3
let ExeB b =
printfn "b"
2
let ExeA =
printfn "a"
1
printfn "Example %d " ExeA
printfn "Example %d " (ExeB 1)
printfn "Example %d " ExeC
The output is as follows...
c
a
Example 1
b
Example 2
Example 3
What seems unusual here is the order that the code is executing in. In a previous question Brian mentioned something about expressions, I was hoping someone could explain this a bit more. It almost seems like the compiler is intelligently pre-executing things to calculate values... but I don't know?
ExeA and ExeC aren't functions, but single values. The compiler ensures that values initialise in the order in which they're declared in the source file, so what's happening here is:
ExeC initialises
ExeA initialises
Example 1 is printed, using ExeA's initialised value
The ExeB function is called as normal
Example 3 is printed, using ExeC's initialised value
If you want ExeA and ExeC to be truly lazy -- that is, to control when their side effects run -- you could turn them into functions that accept unit:
let ExeC () =
printfn "c"
3
let ExeB b =
printfn "b"
2
let ExeA () =
printfn "a"
1
printfn "Example %d " (ExeA ())
printfn "Example %d " (ExeB 1)
printfn "Example %d " (ExeC ())
As a follow up to Tim's answer, I thought you might appreciate some further insight into what you've stumbled upon. In your example, ExeC and ExeA take advantage of the functional style of organizing code through lexical scoping and closures. Let me demonstrate a more powerful example.
let calc n =
//...
let timesPieDiv4 =
let pie = 3.14
let pieDiv4 = pie/4.
n * pieDiv4
//...
Here again timesPieDiv4 is not a function, but does have a body which contains a series of sub calculations which are not exposed to the rest of the calc function. In a language like C#, you have two options neither of which appeals to me. The first option is to simply declare pie and pieDiv4 within the main body of calc, but then it's less clear how they are being used and you dirty your variable space. The other option is to factor those sub calculations out into a separate private helper function. But I dislike such functions, because with many it becomes hard to analyze your complex algorithms since you are constantly darting around looking up various implementation pieces. Plus it's a lot of boiler plate code and value passing. That's why F# functions are "public" by default, lexical scoping and closures allow you to hierarchically organize "private" functions and values within your public facing functions.

Embedding Lua in OCaml

Could you, please, give a code snippet showing how to use Lua embedded in OCaml?
A simple example could be a "Hello, World" variant. Have OCaml prompt the user for a name. Then pass that name to a Lua function. Have Lua print a greeting and return the length of the name. Then have OCaml print a message about the length of the name.
Example:
user#desktop:~$ ./hello.opt
Name? User
Hello, User.
Your name is 4 letters long.
user#desktop:~$
[Edit]
As a non-C programmer, could I implement this without having to write an intermediary C program to pass the data between Lua and OCaml?
Following is a theoretical idea of what I would like to try. Unfortunately, line 3 of ocaml_hello.ml would need to know how to call the function defined in lua_hello.lua in order for the code to be valid.
lua_hello.lua
Defines lua_hello, which prints an argument and returns its length.
1 function lua_hello (name)
2 print ("Hello, "..name..".")
3 return (string.len (name))
4 end
ocaml_hello.ml
OCaml prompts for a name, calls the Lua function, and prints the return value.
1 let () = print_string "Name? "; flush stdout in
2 let name = input_line stdin in
3 let len = Lua_hello.lua_hello name in
4 Printf.printf "Your name is %d letters long." len; flush stdout;;
I'm not aware of a mature set of bindings for embedding the C implementation of Lua into OCaml. An immature set of bindings was posted on the Caml mailing list in 2004.
If you want to use the ML implementation you can find some examples in a paper called ML Module Mania. The ML implementation, unlike the C implementation, guarantees type safety, but to do so it uses some very scurvy tricks in the ML module system. If you are asking basic questions, you probably want to avoid this.
In your example it's a little hard to guess where you want the function to come from. I suggest you either ask for a C example or give people a C example and ask how it could be realized in OCaml (though I think bindings are going to be a problem).
Edit
In response to the revised question, it's pretty complicated. The usual model is that you would put Lua in charge, and you would call Objective Caml code from Lua. You're putting Caml in charge, which makes things more complicated. Here's a rough sketch of what things might look like:
let lua = Lua.new() (* create Lua interpreter *)
let chunk = LuaL.loadfile lua "hello.lua" (* load and compile the file hello.lua *)
let _ = Lua.call lua 0 0 (* run the code to create the hello function *)
let lua_len s =
(* push the function; push the arg; call; grab the result; pop it; return *)
let _ = Lua.getglobal lua "lua_hello" in
let _ = Lua.pushstring lua s in
let _ = Lua.call lua 1 1 in
let len = Lua.tointeger lua (-1) in
let _ = Lua.pop lua 1 in
len
let () = print_string "Name? "; flush stdout
let name = input_line stdin
let len = lua_len name
Printf.printf "Your name is %d letters long." len; flush stdout;;
Again, I don't know where you'll get the bindings for the Lua and LuaL modules.
On further reflection, I'm not sure if you can do this with the official C implementation of Lua, because I think OCaml believes it owns main(). You'd have to find out if OCaml could be packaged as a library from a C main program.
For an example of putting Lua-ML in charge, you can get Lua-ML standalone from Cminusminus.org, and you can also check out the examples in the paper on Lua-ML as well as the source code to the QC-- compiler itself.

Resources