My adventures in ML Land
Tags: functional
Published: 2022-03-20 15:11:06

I thought it might be interesting to document my journey of learning the ML family of languages. I will try to list the resources I used in chronological order (mostly) in the hopes that it might help someone else.

### Discovering and Learning F# #

My first exposure to F# was through these two talks by Scott Wlaschin
- [Functional programming design patterns](https://youtu.be/E8I19uA-wGY)
- [Domain Modeling Made Functional](https://youtu.be/Up7LcbGZFuo)

I am not sure how I got interested in computation expressions but I do remember at some point thinking of ways to use it for implementing a react-hooks clone. After I started reading fsharpforfunandprofit's [Computation expression series](https://fsharpforfunandprofit.com/series/computation-expressions.html), I realized that let-expressions were a key to understanding the concept. A quick google search led to https://www2.lib.uchicago.edu/keith/ocaml-class/definitions.html

Later, I needed to write tokenizer + lexer as a part of an assignment in Nand2Tetris part two. Conveniently, this was when I stumbled on posts about using F# for writing parsers.
- [Understanding parser combinators](https://fsharpforfunandprofit.com/posts/understanding-parser-combinators/).
- [Using FParsec to parse LOGO](http://trelford.com/blog/post/FParsec.aspx)
- [Write your own compiler in 24 hours](https://youtu.be/-E2tu3MqR24)


### Things I didn't like about F# #

- Use of XML in fsproj
- Optional and named arguments not being available to normal functions
- Not CLI friendly as other languages. `dotnet-cli` is attempting to fill this gap but it is not quite there yet.
- Cannot create a native executable that can be easily distributed.

### Moving to OCaml

Because F# was originally inspired by OCaml which doesn't have any of the pet peeves I had with F#, I decided I should give OCaml a try
- [OCaml basics](https://ocaml.org/learn/tutorials/basics.html) and [structure of ocaml programs](https://ocaml.org/learn/tutorials/structure_of_ocaml_programs.html)
- [A Crash Course in OCaml Modules](https://youtu.be/lISWTUyNP4c)
- [OCaml alternative syntax for F# computation expressions] (https://jobjo.github.io/2019/04/24/ocaml-has-some-new-shiny-syntax.html)
- [Opam docs](https://opam.ocaml.org/doc/)

I wanted to write an HTTPie clone in OCaml. To do that, I started reading [Real World OCaml](https://dev.realworldocaml.org/index.html) to better familiarize myself with the language. 

Real World OCaml uses [Base](https://github.com/janestreet/base) to replace OCaml's stdlib. I am not very fond of Base since it deviates from the standard convention of passing functions before values in HOC. To fix the ordering, one has to use labels:

```fsharp
open Base

[1;2;3;4] |> List.map ~f:(fun x -> x * 2)
```

Fortunately, there is [Containers](https://github.com/c-cube/ocaml-containers) which gets the argument ordering right.

```fsharp
open Containers

[1;2;3;4] |> List.map (fun x -> x * 2)
```

To write OCaml code, I sat up Neovim by following this [guide](https://www.rockyourcode.com/setup-ocaml-with-neovim/). For my repl needs, I used [Utop](https://github.com/ocaml-community/utop). Whenever I needed to insert multiple lines, I used Utop's $editor integration which could be opened by C-x C-e.

There is a lot to be desired about OCaml tooling, but I am really excited about [opam-tools](https://github.com/avsm/opam-tools) and [duniverse](https://github.com/ocamllabs/duniverse).

### Haskell
While searching for OCaml twitch streams, I stumbled on tsoding channel which does mostly Haskell and occasionally some OCaml.

- [Compiler" in OCaml](https://www.twitch.tv/tsoding/video/654258168)
- [JSON Parser 100% From Scratch in Haskell](https://youtu.be/N9RUqGYuGfw)
- [What is IO monad?](https://www.youtube.com/watch?v=fCoQb-zqYDI)

Later, I watched some videos about Elm which counterintuitively made me fall in love with Haskell.

* More concise syntax for lambda declaration
* Types taking their own line
* Infix operators with customizable associativity and precedence.
* Can be compiled into a single binary. 
* Type classes.

One thing I missed in Haskell was F#'s pipeline operator. Fortunately, It can be easily defined.

```haskell
λ> import Data.Function ((&))
λ> (|>) = (&)
λ> (<|) = ($)
λ> [1..10] |> filter even |> map (\x -> x * 2)
```

- [Try haskell](https://tryhaskell.org/)
- [Haskell the hard way](https://yannesposito.com/Scratch/en/blog/Haskell-the-Hard-Way/)
- [Haskell beginner crash course](https://typeclasses.com/beginner-crash-course)
- [CIS 194: Introduction to Haskell (Spring 2013)](https://www.seas.upenn.edu/~cis194/spring13/lectures/01-intro.html)