I Love OCaml
Why I love OCaml
Every morning, I wake up and ask myself: why isn’t OCaml more
popular? I mean, the language is not perfect, but the more I use it the
more I feel like this old language had it all figured out, somehow. I
mean, not in the literal sense: you write String.of_X
instead of String.from_X because the language has French
origins. But it is perfect in the sense that it has everything that is
important to me, except popular adoption. OCaml has its quirks, its old
age, but at the same time there is so much I appreciate about it.
I have some experience building amateur and professional software, in many different languages, and as a result I have collected a list of characteristics that I’ve come to appreciate over time. I think my journey into programming is different from many. I learned and adored functional programming before working in the industry, and while not my very first language, Haskell was important to me early on. Functional programming has allowed me to break big, complex problems down into subproblems that I know how to solve. It has made me a better thinker. Add to that the static guarantees of Haskell, which makes the mental overhead much lower than for other languages, and I am also more productive. Most importantly, with Haskell, I can focus more on the fun parts of programming.
However, Haskell’s issues lie in its immense complexity and slow compile times. I did say that Haskell lowers the mental overhead of programming, but that’s only if you use a small subset of the language. However because much of the community is very maximalist, introducing a lot of complexity into the code becomes inevitable. Much of the code you interact with is too “smart”, and becomes very hard to grok. Its runtime is also very complex, and there’s always the chance of running into notorious “space leaks”, that are extremely hard to debug.
At some point, I started exploring a language that is probably the polar opposite to Haskell: Go. With Go, I learned to appreciate simplicity and low-levels of abstractions, a good set of tooling, fast performance and fast compilation speed. I also started to appreciate good documentation that is easily available offline. The culture around Go also places a lot of value on simple solutions, which made interacting with the ecosystem easier. I can jump into any code base and understand what is happening.
Over time, I also grew to hate the issues that come with the language being so conservative: it is verbose in its error handling yet manages to be fragile. At the same time, it doesn’t have explicit null checks. These factors combined makes Go quite unpleasant and easy to write buggy code in. I also found myself missing a REPL or fast way of interacting with the program. The language is “predictably disappointing”, which I guess is a good thing. However, the solutions to those disappointments have been around before the language was even created and I am just left feeling that these solutions could have been implemented, and the compiler would not be much more complex as a result. It just genuinely felt like the Go language designers didn’t want to engage with any of the ideas coming from functional programming. But I digress.
From these experiences, a list of features I consider to be “good” features in a general programming language started to emerge:
- Fast compile times
- Fewer abstractions, and an easy to understand runtime
- Strong static guarantees
- Functional programming constructs. Especially pattern matching and sum types.
- Good performance
- Good documentation
And then, enter OCaml. This language just checks so many boxes:
- Strong static guarantees. Sum types, polymorphic variants, pattern matching.
- Simpler runtime semantics. OCaml is weird in that it’s a garbage collected language for systems, similar to Go. A seasoned OCaml programmer is probably able to gauge what the compiled assembler looks like just by looking at the code. That is a great quality.
- Fast compile times. When using Haskell or Rust, the slow compile times really kill your productivity. With Dune, OCaml compiles extremely fast. Faster than Go I believe?
- Similar to Go, OCaml can be compiled statically into a single binary, making it easy to deploy.
- Great documentation. OCaml has odig to browse documentation offline, utop as a REPL to explore code, and also separates interface files from implementation files. This makes it very pleasant to browse OCaml code. The types help guide the user.
- Automatically inferred types. I didn’t think this would matter, as writing out the types used to help my thinking. But now that I am more “fluent”, it is more typing and less code. In OCaml, modules separate interface files from implementation, and these are a better place to put types.
I’m left feeling that the authors of OCaml have good taste. It is an old language, and there are a few features that could probably be left out like the OOP-related features, and some libraries in the ecosystem over-complicate things like in Haskell. But overall, it’s just damn good. There are a lot of other features I appreciate about OCaml that I didn’t share. But to summarize why I love it: the right balance between simple and expressive, good documentation and good tooling.
What's Your Reaction?
Like
0
Dislike
0
Love
0
Funny
0
Angry
0
Sad
0
Wow
0