Hyperpolyglot ML Dialects and Haskell: SML, OCaml, F#, Haskell

lambertsimnel1 pts0 comments

ML Dialects and Haskell: SML, OCaml, F#, Haskell - Hyperpolyglot

Hyperpolyglot

ML Dialects and Haskell: SML, OCaml, F#, Haskell

a side-by-side reference sheet

grammar and invocation | variables and expressions | arithmetic and logic | strings | dates and time | arrays | lists | tuples | dictionaries | functions | execution control | exceptions | concurrency | file handles | files | directories | processes and environment | libraries and namespaces | user-defined types | objects | inheritance and polymorphism | net and web | unit tests | debugging and profiling | repl

sml<br>ocaml<br>f#<br>haskell

version used

SML NJ 110<br>4.0<br>F# 3.0

Mono 3.2<br>7.4

show version

displayed at startup<br>$ ocaml -version<br>$ fsharpi --help<br>$ ghc --version

grammar and invocation

sml<br>ocaml<br>f#<br>haskell

interpreter

$ echo 'print_endline "hello"' > hello.ml

$ ocaml hello.ml<br>$ cat EOF > hello.fs

module hello

let main = printfn "hello"

EOF

$ fsharpi --quiet --exec hello.fs<br>$ echo 'main = putStrLn "hello"' > hello.hs

$ runghc hello.hs

shebang

$ cat EOF > hello.ml

#!/usr/bin/env ocaml

print_endline "hello";;

EOF

$ chmod +x hello.ml

$ ./hello.ml<br>$ cat EOF > hello.fs

#light (*

exec fsharpi --exec $0 --quiet

*)

module hello

printfn "hello"

EOF

$ chmod +x hello.fs

$ ./hello.fs<br>$ cat EOF > hello.hs

#!/usr/bin/env runghc

main = putStrLn "hello"

EOF

$ chmod +x hello.hs

$ ./hello.hs

bytecode compiler and interpreter

$ echo 'print_endline "hello";;' > hello.ml

$ ocamlc -o hello hello.ml

$ ocamlrun hello<br>$ echo 'printfn "hello"' > hello.fs

$ fsharpc hello.fs

$ mono hello.exe<br>none

native compiler

$ echo 'print_endline "hello";;' > hello.ml

$ ocamlopt hello.ml -o hello

$ ./hello<br>none<br>$ echo 'main = putStrLn "hello"' > hello.hs

$ ghc -o hello hello.hs

$ ./hello

library which is always imported

Pervasives<br>Core<br>Prelude

statement terminator<br>;;<br>;;<br>next line has equal or less indentation, or ;

blocks<br>( expr ; … )<br>( expr ; … )

begin expr ; … end<br>( expr ; … )

begin expr ; … end<br>offside rule or { }

end-of-line comment<br>none<br>none<br>// comment<br>-- comment

multiple line comment<br>(* comment

another comment *)<br>(* comment

another comment *)<br>(* comment

another comment *)<br>{- comment

another comment -}

variables and expressions

sml<br>ocaml<br>f#<br>haskell

write-once variable

val a = 3;<br>let n = 1 + 2;;<br>let n = 1 + 2<br>n = 3

modifiable variable<br>val a = ref 3;

a := 4;

!a + 7;<br>let n = ref 3;;

n := 4;;

!n + 7;;<br>let n = ref 3

n := 4

!n + 7

unit type and value<br>unit

()<br>unit

()<br>unit

()<br>()

()

conditional expression<br>val x = 3;

if x<br>let n = -3;;

let absn = if n<br>let n = -3

let absn = if n<br>n = -3

let absn = if n

branch type mismatch<br>(* compilation error: *)

if true then "hello" else 3;<br>(* compilation error: *)

if true then "hello" else 3;;<br>(* compilation error: *)

if true then "hello" else 3<br>-- compilation error:

if True then "hello" else 3

null

NONE<br>None<br>None

Also this value returned by .NET library functions. It has a type distinct from None:

null<br>Nothing

nullable type<br>type list_option_int = int option list;

val list = [SOME 3,NONE, SOME ~4];<br>type list_option_int = int option list;;

let list = [Some 3; None; Some (-4)];;

list = [Just(3), Nothing, Just(-4)]

null test

match foo with

| None -> true

| _ -> false;;

coalesce<br>val foo = SOME 3;

(* raises exception if NONE: *)

valOf foo;

(* evaluates to 0 if NONE: *)

getOpt (foo, 0);<br>match foo with

| None -> 0

| Some n -> n;;

import Data.Maybe

let foo = Just(3)

raises exception if Nothing:

fromJust foo

let intId x = x

evaluates to 0 if Nothing:

maybe 0 intId foo

nullif

match foo with

| -999 -> None

| n -> Some n;;

expression type declaration

float 1<br>float 1<br>1 :: Double

let ... in ...<br>val z =

let

val x = 3.0

val y = 2.0 * x

in

x * y

end;<br>let z =

let x = 3.0 in

let y = 2.0 *. x in

x *. y;;<br>let z =

let x = 3.0 in

let y = 2.0 * x in

x * y<br>z = let x = 3.0

y = 2.0 * x

in x * y

where<br>none<br>none<br>none<br>z = x * y

where x = 3.0

y = 2.0 * x

arithmetic and logic

sml<br>ocaml<br>f#<br>haskell

boolean type

bool<br>bool<br>bool<br>Bool

true and false

true false<br>true false<br>true false<br>True False

logical operators<br>andalso orelse not<br>&& || not<br>&& || not<br>&& || not

relational operators<br>= <> =<br>= <> =<br>= <> =<br>== /= =

min and max

min 1 2

max 1 2<br>min 1 2

max 1 2<br>min 1 2

max 1 2

integer type<br>int<br>int

other integer types:

int32 int64 nativeint<br>int

other integer types:

int32 int64 nativeint<br>Integer

integer literal<br>negative integer:

~4<br>int, int64, and nativeint literals:

12 12L 12n

literals can contain underscores:

1_000_000

this parses as an expression:

-4<br>-4<br>an expression, not a literal:

-4

float type<br>real<br>float<br>float<br>Double

integer operators<br>+ - * div mod<br>+ - * / mod

mod //is an infix operator<br>+ - * / %<br>+ - * div rem

div and rem are functions, not infix operators

float operators

+ - * /<br>+. -. *. /.<br>+ - * /<br>+ - * /

add integer and float<br>real 3 + 7.0;<br>float 3 +. 7.0<br>float 3 + 7.0<br>3 + 7.0

integer division

and remainder<br>7 div 3

7 mod 3

real 7 /...

hello none comment haskell ocaml type

Related Articles