Haskell as a Lens
Through Ruby, we have examined names, types, functions, and objects. We now turn our attention to Haskell, a language that is very different from others you have learned. In Ruby and other imperative languages, we bark orders at the computer. In Haskell, which is a functional language, we produce values. Functional languages are functional because in them functions—which produce values—are the most important building block for writing programs. They also some lack several features that we consider vital in imperative languages, like loops and mutability.
A surplus of functional languages emerged in the 1980s. A group of programming language researchers decided to coordinate their efforts and build a superlanguage that would unify the fragmented community. The result was Haskell, the first specification of which was released in 1990. The language was named after Haskell Curry, a mathematician whose theoretical work showed that certain kinds of mathematical proofs can be expressed as computer programs. After the language was released, Curry's widow informed the language committee that her husband despised his first name. Too late. The name was immutable.
The Haskell language has grown over the last 30 years, but it has never reached a level of adoption that would make it a household name. You may question the utility of studying a language that you haven't heard of before, but a language's popularity is not a reliable measure of its worth. Companies big and small do employ Haskell programmers and fund its open-source development. Meta uses Haskell to fight spam on Facebook. Tesla uses it to run self-driving cars. Co-star proudly uses Haskell to power their astrology app. The New York Times uses it to power parts of their website.
There are several reasons to study Haskell even though it has not wooed developers to the same degree as JavaScript, C++, and Java. First, Haskell presents the ideas of functional programming in an ultra-concentrated form, and we can't help but learn these ideas as we work with the language. We can then take these ideas to other languages that we regularly use. Second, new programming language ideas are more likely to appear in smaller research languages like Haskell. Mainstream languages will always lag in features because they are encumbered by technological inertia. Third, software written in Haskell tends to be safe and fast. Companies use many languages across their product line, playing to the strengths of each language. Haskell has a reputation for being used to rewrite components that run slowly or have concurrency bugs. Programs rewritten in Haskell generally require less code, have fewer bugs, and are faster to develop.
In this chapter, we introduce Haskell and briefly examine one of several ways to define functions. But we focus on the basic building block of functions: expressions, which yield values. Imperative languages have expressions too, but these are embedded within statements, which produce side effects like writing memory and performing I/O. By the end of the chapter, you'll be able to answer the following questions:
- What is Haskell's type system? Are types explicit, implicit, or optional? Is typechecking performed statically or dynamically? How are functions written polymorphically so they can serve many types?
- Operators glue expressions together to form compound expressions. What are the semantic qualities of these operators? Can new operators be defined?
- How does a programmer choose between values using conditional logic?
- When and how is an expression evaluated?
Haskell is the language we have chosen as a lens to examine expressions and functional programming. We could instead have chosen a language from the Lisp family, whose best-known dialects are Common Lisp, Racket, Scheme, and Clojure. The designers of these languages have contributed a number of significant ideas to programming language design, including garbage collection, recursive functions and data structures, and dynamic typing. That we did not choose one of these languages is largely a matter of chance and personal taste, not of some objective rank.