Page 2 of 3
A new hope
Due to the problems I observed with Haskell, I finally understood the appeal of languages like OCaml, Scala or F#.
Broadly speaking, they are similar to Haskell in that they emphasize functional paradigms, but they are strict, have first class support for mutability (apart from immutability) and imperative programming paradigms. Of course each of them comes with its own baggage of new concepts and ecosystem-wise there are quite a lot of differences.
So far I’ve tried to play a bit with Scala again, but.. I can’t really put my finger on it but I can’t like the language. It’s probably because Scala seems to be even quite a bit more complex than Haskell and there seem to be so many ways to achieve a task. F# seems to be too .NET centric and OCaml seems to have its share of its own problems but that doesn’t mean that I don’t want to check it out someday.
Choosing a language for a project
I think now it’s a good time to explain that I had a small to medium project in mind that I wanted to implement as elegantly as possible. In order to compare the different languages I tried to implement it in some of them.
I first started with Haskell. Algebraic datatypes, immutability, the help of the type system, automatically derived type classes, type classes in general and some syntactic virtues of Haskell made the beginning of the project really pleasant. However, when it came to state shuffling, monadic code paired with the unforgiving record (updating) syntax I soon felt that the elegance was gone.
Next in line was Java. Ironically, using the “unsexy” Java language I almost fully implemented my project, which hadn’t been the case for the Haskell version although I really felt that missing support for algebraic datatypes, immutability, null pointer safety, first class functions and closures, conciseness and the interlocking of namespaces, classes and files made a lot of things unnecessary cumbersome and unclear. For instance, I had to manually provide copy, equals and hash methods, I had to make silly classes like
Pair due to a lack of tuples, had to create classes where a simple closure would have sufficed etc.
Still, the uncumbersome way of writing down control flow, post-fix accessing of methods/fields on a class, great IDE support and first class field manipulation support made up for the weaknesses, that is, just so much that I still had motivation to almost finish the project.
I also tried to implement it with Scala but I ran into some problems that I could not solve elegantly so I didn’t get very far.
Wouldn’t it be great to combine the best parts of languages like Java and languages like Haskell without creating a language that is as complex as Scala?
Well, it turns out there are some interesting new alternative programming languages that make some of the wishes true or at least are able to improve some of the aforementioned pain points. Let me just list them and afterwards talk a bit about each:
Idris and Disciple are quite close to Haskell. I don’t actually know much about each of them apart from them being syntactically similar to Haskell but strict-by-default. This is what I discovered about their features on their respective homepages.
Idris is a general purpose pure functional programming language with dependent types. Dependent types allow types to be predicated on values, meaning that some aspects of a program’s behaviour can be specified precisely in the type. It is compiled, with eager evaluation. Its features are influenced by Haskell and ML.
I never used a dependently typed language but what I understood broadly is that you can encode more properties about your program statically in the type system. The advantages notwithstanding, this seems to lead to far reaching implications regarding the practical usefulness of a language with respect to general purpose programming. Idris wants to find the sweet spot between practicality and power of the type system. In any case, I mostly listed the language here as a reminder for me to check it out sometime.
Disciple is a dialect of Haskell that uses strict evaluation as the default and supports destructive update of arbitrary data structures. Disciple includes region, effect and closure typing, and this extra information provides a handle on the operational behaviour of code that isn’t available in other languages. Programs can be written in either a pure/functional or effectful/imperative style, and one of our goals is to provide both styles coherently in the same language.
Disciple is not a dependently typed programming language. It is very similar to Haskell in that it even claims on its homepage that a lot of already written Haskell programs would be valid Disciple programs, albeit with some minor modifications here and there. The characterising feature of this language seems to be an effect system.
Without understanding what an effect system is or how this or that is implemented one can still take a look at the language overview on Disciple’s homepage and learn that seemingly the main complaints of mine regarding Haskell above are solved in Disciple. Namely, strict evaluation by default with optional lazy evaluation, first class mutability support, first class field manipulation support. Disciple seems to be great at first glance.