what the fuck do people use haskell for

a realistic answer is “not much” as haskell has failed to escape academia to any reasonable degree for several reasons i’ll get to in a bit

an optimistic answer is “a few things” such as xmonad (a window manager which i have used for years), darcs (a VCS used pretty much solely for haskell packages) and some other shit that doesn’t really matter

the problem with haskell is that it is specified and perpetuated officially by academic bodies who have an interest in keeping it purely functional. wtf is a ‘purely functional’ language?

‘functional’ languages are those whose paradigm follows functional principles. in english, this means the language strives to adhere to a handful of well-defined and specific traits of functional languages like state immutability and wide equivalence w/r/t identifier evaluation strategies

what THAT means, in english, is that to write a program in a functional language you lay out all your data up front and have your program deal with it through functional operations. these functions are fundamentally mathematical meaning their output shouldn’t differ according to the program state

what i mean by “laying out all your data up front” is that your types/variables/whatever don’t ever change throughout the execution of your program. they are immutable meaning they are immune to mutation. this is kind of what makes functional languages relevant in any capacity, as without state mutations you preclude “side effects” which are the changes is program state (usually ones that wouldn’t logically follow the operation causing them) that tend to cause instability in non-functional languages. let me explain further:

having a globally immutable state is a very weird thing when you’re writing code. to someone who has only written C their whole life (or python/js/ruby/whatever) this seems impossible at first glance. you can’t just define a variable and do whatever you want with it. you can’t wantonly change your variables or check them in control sequences, see, that all has to do with mutable states (since you are mutating your variables and having your program operate according to the mutated states, which could be anything, hence side effects/instability)

instead, you code from bottom-up starting with the resolute details of your program. a program that takes an input string and calculates its SHA256 hash, for example, would start with a variable describing the input text (which would never change, obviously) and a function that transforms the input type, using only mathematical means, to an output type (which would also never change, because the SHA-2 algo doesn’t change). you’d then define an output variable as the result of the unchanging input variable fed to the unchanging hash function

see, your program becomes a lot clearer because everything is very strictly and tightly defined, and it all boils down to simple mathematical operations. in imperative languages, when you do something like nest multiple if statements or nest if statements in switch blocks that may not have every case covered, the number of discrete possible paths your program could take during execution rapidly explodes into a number larger than the # of atoms in the known universe. when state changes, and multiple state changes exist at different times with control sequences operating according to those changes nested together, your permutation count devolves into something unreasonable

functional languages avoid this permutation explosion which makes it possible to sanely predict how your program will run, making bugfixes easier and more importantly making correctly-written programs extremely, extremely stable

NOW

haskell is a particular case, as it is not only a functional language, but a purely functional language. this means that there is no language-defined way for you to deviate out of this functional paradigm. it follows every virtue of functional languages and it follows them as zealously as possible. this is cool in theory because it means that no matter what you write in haskell, no matter how many hundreds of thousands of lines incorporating every library, language mechanism, or whatever, if it is valid haskell syntax then it will have all the positive qualities mentioned before

that sounds like it would be cool. it sounds like haskell would be a superior programming language in every way. but in reality it starts to really suck in several ways:

1. haskell (and other functional languages) are premised in mathematical/logical/statistical fields of study and not in computer science. its original architects were mostly logicians and mathematicians applying their field of study to computer science. the result is that solving problems in functional languages is often an incredibly laborious and difficult task and very hard to model in the context of a functional environment. these problems are much, much easier to solve in a imperatively language, comparatively. there is a huge discontinuity between the tools haskell provides and the problems you encounter writing a program on a computer. for example!

earlier, i said that purely functional languages implicate an absolute, immutable state. if you can’t change the state, how the fuck could you possible do any kind of I/O? I/O categorically refers to dealing with information you can’t possibly know or attempt to discern before you actually deal with it, and on the surface it seems impossible to reconcile both IO mechanisms and functional paradigms

there is a solution to this problem! the solution is monads. do i understand how monads work? fuck no! why not? because:

image

the pathways you must use in a functional language really, really do not suit the problems you are trying to solve with a computer. it’s like removing nails with a pair of scissors instead of the back of a hammer

2. it is god damn unreasonably hard to compile haskell source into actual programs that can run on your computer. it’s even harder to do this efficiently (as to make compilation times quick) and even fucking harder to optimize output (as to make compiled programs run faster). in the last reason, i purported a discrepancy between what tools haskell provides you with versus the tools needed to solve the problems you will encounter. the discrepancy between the logical system you create writing haskell source code in a text editor with english keywords and operators and the actual sequence of processor instructions corresponding to the source is even wider. let me demonstrate:

any good programming language is bootstrapped, meaning the compiler of that language is written in the language it aims to compile. the C compiler is written in C, the golang compiler is written in go. the haskell compiler is written in haskell. it is called ghc. let’s take a look at ghc:

image

fucking 900 megabytes. almost a gig for a fucking compiler. ghc is hands down the largest body of solely program text i’ve ever hard to deal with. there are no images/documents/models/whatever in that directory. just binaries. compare:

image

i highlighted the byte-count. 2376139 bytes = ~2.3 MB. a little over 2 megs and you have what you need to run an entire operating system from the ground up

the result of this is that programs written in haskell are exponentially more resource-hungry than equivalents in imperative languages.

3. haskell goes ham with the whole ‘purely functional’ thing. purely functional languages are cool and useful to logicians whose problems only exist on paper in university libraries. for the reasons i’ve listed, haskell is never a smart choice for a real problem

HOWEVER

the ‘functional’ aspect is not to blame, only haskell’s extremist approach to it. there are languages that incorporate just some aspects of functional languages and retain just some of the desired qualities but present the language in a (ironically) functional way you can actually do shit with. an example is erlang. erlang is a fucking awesome language. our phone systems, at a high level, rely on computers running programs written in erlang. if you don’t already know, keeping phone systems online and operational is about as important as keeping g-d life support systems online and operational. we measure the quality of service of telephone systems in nines i.e. 5 nines of reliability. this would refer to a system that is operational 99.999% of the time (see, five nines)

when we absolutely must use software to control telephone systems at very high, abstract levels, we do so with software written in erlang. the whole “no side effect” thing and “no unpredictable crazy behavior” thing make it an acceptable choice. you can also do other really crazy shit like replace code portions during runtime without interrupting parts of the program unaffiliated with the part you’re replacing. erlang’s saving grace is that it is not entirely a functional languages, it makes compromises that make it a workable language that you can use without wanting to slam your arms in car doors constantly

this is probably way more than you wanted to hear but you knew what you were signing up for

image