{"id":18041352,"url":"https://github.com/ligurio/clojure-from-the-ground-up","last_synced_at":"2025-06-14T13:36:38.600Z","repository":{"id":45909628,"uuid":"283717474","full_name":"ligurio/clojure-from-the-ground-up","owner":"ligurio","description":"Book about Clojure written by Kyle Kingsbury https://aphyr.com/tags/Clojure-from-the-ground-up, formatting and conversion to Markdown, EPUB and HTML by Sergey Bronnikov.","archived":false,"fork":false,"pushed_at":"2024-05-08T14:58:41.000Z","size":567,"stargazers_count":21,"open_issues_count":0,"forks_count":2,"subscribers_count":3,"default_branch":"master","last_synced_at":"2025-03-23T18:54:21.872Z","etag":null,"topics":["book","clojure","programming","programming-language"],"latest_commit_sha":null,"homepage":"https://bronevichok.ru/static/Kyle_Kingsbury_Clojure_From_The_Ground_Up.html","language":"Makefile","has_issues":false,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/ligurio.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2020-07-30T08:44:19.000Z","updated_at":"2024-08-17T21:08:06.000Z","dependencies_parsed_at":"2022-08-25T13:41:28.582Z","dependency_job_id":null,"html_url":"https://github.com/ligurio/clojure-from-the-ground-up","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ligurio%2Fclojure-from-the-ground-up","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ligurio%2Fclojure-from-the-ground-up/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ligurio%2Fclojure-from-the-ground-up/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/ligurio%2Fclojure-from-the-ground-up/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/ligurio","download_url":"https://codeload.github.com/ligurio/clojure-from-the-ground-up/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248073053,"owners_count":21043356,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["book","clojure","programming","programming-language"],"created_at":"2024-10-30T15:09:14.579Z","updated_at":"2025-04-09T16:51:42.866Z","avatar_url":"https://github.com/ligurio.png","language":"Makefile","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Clojure from the ground up\n\n## Welcome\n\nThis guide aims to introduce newcomers and experienced programmers alike to the\nbeauty of functional programming, starting with the simplest building blocks of\nsoftware. You’ll need a computer, basic proficiency in the command line, a text\neditor, and an internet connection. By the end of this series, you’ll have a\nthorough command of the Clojure programming language.\n\n### Who is this guide for?\n\nScience, technology, engineering, and mathematics are deeply rewarding fields,\nyet few women enter STEM as a career path. Still more are discouraged by a\nculture which repeatedly asserts that women lack the analytic aptitude for\nwriting software, that they are not driven enough to be successful scientists,\nthat it’s not cool to pursue a passion for structural engineering. Those few\nwith the talent, encouragement, and persistence to break in to science and tech\nare discouraged by persistent sexism in practice: the old boy’s club of tenure,\nbeing passed over for promotions, isolation from peers, and flat-out assault.\nThis landscape sucks. I want to help change it.\n\nWomen Who Code, PyLadies, Black Girls Code, RailsBridge, Girls Who Code, Girl\nDevelop It, and Lambda Ladies are just a few of the fantastic groups helping\nwomen enter and thrive in software. I wholeheartedly support these efforts.\n\nIn addition, I want to help in my little corner of the technical\ncommunity–functional programming and distributed systems–by making high-quality\neducational resources available for free. The\n[Jepsen](https://aphyr.com/tags/jepsen) series has been, in part, an effort to\nshare my enthusiasm for distributed systems with beginners of all stripes–but\nespecially for women, LGBT folks, and people of color.\n\nAs technical authors, we often assume that our readers are white, that our\nreaders are straight, that our readers are traditionally male. This is the\ninvisible default in US culture, and it’s especially true in tech. People\ncontinue to assume on the basis of my software and writing that I’m straight,\nbecause well hey, it’s a statistically reasonable assumption.\n\nBut I’m not straight. I get called faggot, cocksucker, and sinner. People say\nthey’ll pray for me. When I walk hand-in-hand with my boyfriend, people roll\ndown their car windows and stare. They threaten to beat me up or kill me. Every\nday I’m aware that I’m the only gay person some people know, and that I can\nshow that not all gay people are effeminate, or hypermasculine, or ditzy, or\nobsessed with image. That you can be a manicurist or a mathematician or both.\nBeing different, being a stranger in your culture, comes with all kinds of\nchallenges. I can’t speak to everyone’s experience, but I can take a pretty\ngood guess.\n\nAt the same time, in the technical community I’ve found overwhelming warmth and\nsupport, from people of all stripes. My peers stand up for me every day, and\nI’m so thankful–especially you straight dudes–for understanding a bit of what\nit’s like to be different. I want to extend that same understanding, that same\nempathy, to people unlike myself. Moreover, I want to reassure everyone that\nthough they may feel different, they do have a place in this community.\n\nSo before we begin, I want to reinforce that you can program, that you can do\nmath, that you can design car suspensions and fire suppression systems and\nspacecraft control software and distributed databases, regardless of what your\nclassmates and media and even fellow engineers think. You don’t have to be\nwhite, you don’t have to be straight, you don’t have to be a man. You can grow\nup never having touched a computer and still become a skilled programmer. Yeah,\nit’s harder–and yeah, people will give you shit, but that’s not your fault and\nhas nothing to do with your ability or your right to do what you love. All it\ntakes to be a good engineer, scientist, or mathematician is your curiosity,\nyour passion, the right teaching material, and putting in the hours.\n\nThere’s nothing in this guide that’s just for lesbian grandmas or just for\nmixed-race kids; bros, you’re welcome here too. There’s nothing dumbed down.\nWe’re gonna go as deep into the ideas of programming as I know how to go, and\nwe’re gonna do it with everyone on board.\n\nNo matter who you are or who people think you are, this guide is for you.\n\n### Why Clojure?\n\nThis book is about how to program. We’ll be learning in Clojure, which is a\nmodern dialect of a very old family of computer languages, called Lisp. You’ll\nfind that many of this book’s ideas will translate readily to other languages;\nthough they may be [expressed in different\nways](http://aphyr.com/posts/266-core-language-concepts).\n\nWe’re going to explore the nature of syntax, metalanguages, values, references,\nmutation, control flow, and concurrency. Many languages leave these ideas\nimplicit in the language construction, or don’t have a concept of metalanguages\nor concurrency at all. Clojure makes these ideas explicit, first-class language\nconstructs.\n\nAt the same time, we’re going to defer or omit any serious discussion of static\ntype analysis, hardware, and performance. This is not to say that these ideas\naren’t important; just that they don’t fit well within this particular\nnarrative arc. For a deep exploration of type theory I recommend a study in\nHaskell, and for a better understanding of underlying hardware, learning C and\nan assembly language will undoubtedly help.\n\nIn more general terms, Clojure is a well-rounded language. It offers broad\nlibrary support and runs on multiple operating systems. Clojure performance is\nnot terrific, but is orders of magnitude faster than Ruby, Python, or\nJavascript. Unlike some faster languages, Clojure emphasizes safety in its type\nsystem and approach to parallelism, making it easier to write correct\nmultithreaded programs. Clojure is concise, requiring very little code to\nexpress complex operations. It offers a REPL and dynamic type system: ideal for\nbeginners to experiment with, and well-suited for manipulating complex data\nstructures. A consistently designed standard library and full-featured set of\ncore datatypes rounds out the Clojure toolbox.\n\nFinally, there are some drawbacks. As a compiled language, Clojure is much\nslower to start than a scripting language; this makes it unsuitable for writing\nsmall scripts for interactive use. Clojure is also not well-suited for\nhigh-performance numeric operations. Though it is possible, you have to jump\nthrough hoops to achieve performance comparable with Java. I’ll do my best to\ncall out these constraints and shortcomings as we proceed through the text.\n\nWith that context out of the way, let’s get started by installing Clojure!\n\n### Getting set up\n\nFirst, you’ll need a Java Virtual Machine, or JVM, and its associated\ndevelopment tools, called the JDK. This is the software which runs a Clojure\nprogram. If you’re on Windows, install [Oracle JDK\n1.7](http://www.oracle.com/technetwork/java/javase/downloads/index.html). If\nyou’re on OS X or Linux, you may already have a JDK installed. In a terminal,\ntry:\n\n```clojure\nwhich javac\n```\n\nIf you see something like\n\n```clojure\n/usr/bin/javac\n```\n\nThen you’re good to go. If you don’t see any output from that command, install\nthe appropriate [Oracle JDK\n1.7](http://www.oracle.com/technetwork/java/javase/downloads/index.html) for\nyour operating system, or whatever JDK your package manager has available.\n\nWhen you have a JDK, you’ll need [Leiningen](http://leiningen.org/), the\nClojure build tool. If you’re on a Linux or OS X computer, the instructions\nbelow should get you going right away. If you’re on Windows, see the Leiningen\npage for an installer. If you get stuck, you might want to start with a [primer\non command line basics](http://blog.teamtreehouse.com/command-line-basics).\n\n```shell\nmkdir -p ~/bin\ncd ~/bin\ncurl -O https://raw.githubusercontent.com/technomancy/leiningen/stable/bin/lein\nchmod a+x lein\n```\n\nLeiningen automatically handles installing Clojure, finding libraries from the\ninternet, and building and running your programs. We’ll create a new Leiningen\nproject to play around in:\n\n```shell\ncd\nlein new scratch\n```\n\nThis creates a new directory in your homedir, called `scratch`. If you see\n`command not found` instead, it means the directory `~/bin` isn’t registered with\nyour terminal as a place to search for programs. To fix this, add the line\n\n```shell\nexport PATH=\"$PATH\":~/bin\n```\n\nto the file `.bash_profile` in your home directory, then run `source\n~/.bash_profile`. Re-running `lein new scratch` should work.\n\nLet’s enter that directory, and start using Clojure itself:\n\n```shell\ncd scratch\nlein repl\n```\n\n### The structure of programs\n\nWhen you type `lein repl` at the terminal, you’ll see something like this:\n\n```shell\naphyr@waterhouse:~/scratch$ lein repl\nnREPL server started on port 45413\nREPL-y 0.2.0\nClojure 1.5.1\n    Docs: (doc function-name-here)\n          (find-doc \"part-of-name-here\")\n  Source: (source function-name-here)\n Javadoc: (javadoc java-object-or-class-here)\n    Exit: Control+D or (exit) or (quit)\n\nuser=\u003e\n```\n\nThis is an interactive Clojure environment called a REPL, for “Read, Evaluate,\nPrint Loop”. It’s going to read a program we enter, run that program, and print\nthe results. REPLs give you quick feedback, so they’re a great way to explore a\nprogram interactively, run tests, and prototype new ideas.\n\nLet’s write a simple program. The simplest, in fact. Type “nil”, and hit enter.\n\n```clojure\nuser=\u003e nil\nnil\n```\n\n`nil` is the most basic value in Clojure. It represents emptiness, nothing-doing,\nnot-a-thing. The absence of information.\n\n```clojure\nuser=\u003e true\ntrue\nuser=\u003e false\nfalse\n```\n\n`true` and `false` are a pair of special values called Booleans. They mean exactly\nwhat you think: whether a statement is true or false. `true`, `false`, and `nil` form\nthe three poles of the Lisp logical system.\n\n```clojure\nuser=\u003e 0\n0\n```\n\nThis is the number zero. Its numeric friends are `1`, `-47`, `1.2e-4`, `1/3`, and so\non. We might also talk about *strings*, which are chunks of text surrounded by\ndouble quotes:\n\n```clojure\nuser=\u003e \"hi there!\"\n\"hi there!\"\n```\n\n`nil`, `true`, `0`, and `\"hi there!\"` are all different types of *values*; the nouns of\nprogramming. Just as one could say “House.” in English, we can write a program\nlike `\"hello, world\"` and it evaluates to itself: the string `\"hello world\"`. But\nmost sentences aren’t just about stating the existence of a thing; they involve\n*action*. We need *verbs*.\n\n```\nuser=\u003e inc\n#\u003ccore$inc clojure.core$inc@6f7ef41c\u003e\n```\n\nThis is a verb called `inc`–short for “increment”. Specifically, `inc` is a\n*symbol* which points to a verb: `#\u003ccore$inc clojure.core$inc@6f7ef41c\u003e` – just like\nthe word “run” is a *name* for the *concept* of running.\n\nThere’s a key distinction here–that a signifier, a reference, a label, is not\nthe same as the signified, the referent, the concept itself. If you write the\nword “run” on paper, the ink means nothing by itself. It’s just a symbol. But\nin the mind of a reader, that symbol takes on *meaning*; the idea of running.\n\nUnlike the number 0, or the string “hi”, symbols are references to other\nvalues. when Clojure evaluates a symbol, it looks up that symbol’s meaning.\nLook up `inc`, and you get `#\u003ccore$inc clojure.core$inc@6f7ef41c\u003e`.\n\nCan we refer to the symbol itself, *without* looking up its meaning?\n\n```clojure\nuser=\u003e 'inc\ninc\n```\n\nYes. The single quote `'` escapes a sentence. In programming languages, we call\nsentences `expressions` or statements. A quote says “Rather than *evaluating* this\nexpression’s text, simply return the text itself, unchanged.” Quote a symbol,\nget a symbol. Quote a number, get a number. Quote anything, and get it back\nexactly as it came in.\n\n```clojure\nuser=\u003e '123\n123\nuser=\u003e '\"foo\"\n\"foo\"\nuser=\u003e '(1 2 3)\n(1 2 3)\n```\n\nA new kind of value, surrounded by parentheses: the *list*. LISP originally stood\nfor LISt Processing, and lists are still at the core of the language. In fact,\nthey form the most basic way to compose expressions, or sentences. A list is a\nsingle expression which has *multiple parts*. For instance, this list contains\nthree elements: the numbers 1, 2, and 3. Lists can contain anything: numbers,\nstrings, even other lists:\n\n```clojure\nuser=\u003e '(nil \"hi\")\n(nil \"hi\")\n```\n\nA list containing two elements: the number 1, and a second list. That list\ncontains two elements: the number 2, and another list. *That* list contains two\nelements: 3, and an empty list.\n\n```clojure\nuser=\u003e '(1 (2 (3 ())))\n(1 (2 (3 ())))\n```\n\nYou could think of this structure as a tree–which is a provocative idea,\nbecause *languages* are like trees too: sentences are comprised of clauses, which\ncan be nested, and each clause may have subjects modified by adjectives, and\nverbs modified by adverbs, and so on. “Lindsay, my best friend, took the dog\nwhich we found together at the pound on fourth street, for a walk with her\nmother Michelle.”\n\n```clojure\nTook\n  Lindsay\n    my best friend\n  the dog\n    which we found together\n      at the pound\n        on fourth street\n    for a walk\n      with her mother\n        Michelle\n```\n\nBut let’s try something simpler. Something we know how to talk about.\n“Increment the number zero.” As a tree:\n\n```clojure\nIncrement\n  the number zero\n```\n\nWe have a symbol for incrementing, and we know how to write the number zero.\nLet’s combine them in a list:\n\n```clojure\nclj=\u003e '(inc 0)\n(inc 0)\n```\n\nA basic sentence. Remember, since it’s quoted, we’re talking about the tree,\nthe text, the expression, by itself. Absent interpretation. If we remove the\nsingle-quote, Clojure will *interpret* the expression:\n\n```clojure\nuser=\u003e (inc 0)\n1\n```\n\nIncrementing zero yields one. And if we wanted to increment *that* value?\n\n```clojure\nIncrement\n  increment\n    the number zero\nuser=\u003e (inc (inc 0))\n2\n```\n\nA sentence in Lisp is a list. It starts with a verb, and is followed by zero or\nmore objects for that verb to act on. Each part of the list can *itself* be\nanother list, in which case that nested list is evaluated first, just like a\nnested clause in a sentence. When we type\n\n```clojure\n(inc (inc 0))\n```\n\nClojure first looks up the meanings for the symbols in the code:\n\n```clojure\n(#\u003ccore$inc clojure.core$inc@6f7ef41c\u003e\n  (#\u003ccore$inc clojure.core$inc@6f7ef41c\u003e\n    0))\n```\n\nThen evaluates the innermost list (`inc 0`), which becomes the number 1:\n\n```clojure\n(#\u003ccore$inc clojure.core$inc@6f7ef41c\u003e\n 1)\n```\n\nFinally, it evaluates the outer list, incrementing the number 1:\n\n```clojure\n2\n```\n\nEvery list starts with a verb. Parts of a list are evaluated from left to\nright. Innermost lists are evaluated before outer lists.\n\n```clojure\n(+ 1 (- 5 2) (+ 3 4))\n(+ 1 3       (+ 3 4))\n(+ 1 3       7)\n11\n```\n\nThat’s it.\n\nThe entire grammar of Lisp: the structure for every expression in the language.\nWe transform expressions by *substituting* meanings for symbols, and obtain\nsome result. This is the core of the [Lambda\nCalculus](http://en.wikipedia.org/wiki/Lambda_calculus), and it is the\ntheoretical basis for almost all computer languages. Ruby, Javascript, C,\nHaskell; all languages express the text of their programs in different ways,\nbut internally all construct a tree of expressions. Lisp simply makes it\nexplicit.\n\n### Review\n\nWe started by learning a few basic nouns: numbers like `5`, strings like `\"cat\"`,\nand symbols like `inc` and `+`. We saw how quoting makes the difference between an\n*expression* itself and the thing it *evaluates* to. We discovered symbols as *names*\nfor other values, just like how words represent concepts in any other language.\nFinally, we combined lists to make trees, and used those trees to represent a\nprogram.\n\nWith these basic elements of syntax in place, it’s time to expand our\nvocabulary with new verbs and nouns; learning to represent more complex values\nand transform them in different ways.\n\n## Basic types\n\nWe’ve learned the basics of Clojure’s syntax and evaluation model. Now we’ll\ntake a tour of the basic nouns in the language.\n\n### Types\n\nWe’ve seen a few different values already – for instance, `nil`, `true`, `false`, `1`,\n`2.34`, and `\"meow\"`. Clearly all these things are *different* values, but some of\nthem seem more alike than others.\n\nFor instance, `1` and `2` are *very* similar numbers; both can be added, divided,\nmultiplied, and subtracted. `2.34` is also a number, and acts very much like 1\nand 2, but it’s not quite the same. It’s got *decimal* points. It’s not an\n*integer*. And clearly `true` is *not very* much like a number. What is true plus\none? Or false divided by 5.3? These questions are poorly defined.\n\nWe say that a *type* is a group of values which work in the same way. It’s a\n*property*\t that some values share, which allows us to organize the world into\nsets of similar things. 1 + 1 and 1 + 2 use the *same addition*, which adds\ntogether integers. Types also help us *verify* that a program makes sense: that\nyou can only add together numbers, instead of adding numbers to porcupines.\n\nTypes can overlap and intersect each other. Cats are animals, and cats are\nfuzzy too. You could say that a cat is a *member* (or sometimes “instance”), of\nthe fuzzy and animal types. But there are fuzzy things like moss which *aren’t*\nanimals, and animals like alligators that aren’t fuzzy in the slightest.\n\nOther types completely subsume one another. All tabbies are housecats, and all\nhousecats are felidae, and all felidae are animals. Everything which is true of\nan animal is automatically true of a housecat. Hierarchical types make it\neasier to write programs which don’t need to know all the specifics of every\nvalue; and conversely, to create new types in terms of others. But they can\nalso get in the way of the programmer, because not every useful classification\n(like “fuzziness”) is purely hierarchical. Expressing overlapping types in a\nhierarchy can be tricky.\n\nEvery language has a *type system*; a particular way of organizing nouns into\ntypes, figuring out which verbs make sense on which types, and relating types\nto one another. Some languages are strict, and others more relaxed. Some\nemphasize hierarchy, and others a more ad-hoc view of the world. We call\nClojure’s type system *strong* in that operations on improper types are simply\nnot allowed: the program will explode if asked to subtract a dandelion. We also\nsay that Clojure’s types are *dynamic* because they are enforced when the program\nis run, instead of when the program is first read by the computer.\n\nWe’ll learn more about the formal relationships between types later, but for\nnow, keep this in the back of your head. It’ll start to hook in to other\nconcepts later.\n\n### Integers\n\nLet’s find the type of the number 3:\n\n```clojure\nuser=\u003e (type 3)\njava.lang.Long\n```\n\nSo 3 is a `java.lang.Long`, or a “Long”, for short. Because Clojure is built on\ntop of Java, many of its types are plain old Java types.\n\nLongs, internally, are represented as a group of sixty-four binary digits (ones\nand zeroes), written down in a particular pattern called [signed two’s\ncomplement representation](http://en.wikipedia.org/wiki/Two's_complement). You\ndon’t need to worry about the specifics–there are only two things to remember\nabout longs. First, longs use one bit to store the sign: whether the number is\npositive or negative. Second, the other 63 bits represent the *size* of the\nnumber. That means the biggest number you can represent with a long is 2^63 - 1\n(the minus one is because of the number 0), and the smallest long is -2^63.\n\nHow big is 2^63 - 1?\n\n```clojure\nuser=\u003e Long/MAX_VALUE\n9223372036854775807\n```\n\nThat’s a reasonably big number. Most of the time, you won’t need anything\nbigger, but… what if you did? What happens if you add one to the biggest Long?\n\n```clojure\nuser=\u003e (inc Long/MAX_VALUE)\n\nArithmeticException integer overflow  clojure.lang.Numbers.throwIntOverflow (Numbers.java:1388)\n```\n\nAn error occurs! This is Clojure telling us that something went wrong. The type\nof error was an `ArithmeticException`, and its message was “integer overflow”,\nmeaning “this type of number can’t hold a number that big”. The error came from\na specific *place* in the source code of the program: `Numbers.java`, on line 1388.\nThat’s a part of the Clojure source code. Later, we’ll learn more about how to\nunravel error messages and find out what went wrong.\n\nThe important thing is that Clojure’s type system *protected* us from doing\nsomething dangerous; instead of returning a corrupt value, it aborted\nevaluation and returned an error.\n\nIf you do need to talk about really big numbers, you can use a BigInt: an\narbitrary-precision integer. Let’s convert the biggest Long into a BigInt, then\nincrement it:\n\n```clojure\nuser=\u003e (inc (bigint Long/MAX_VALUE))\n9223372036854775808N\n```\n\nNotice the N at the end? That’s how Clojure writes arbitrary-precision integers.\n\n```clojure\nuser=\u003e (type 5N)\nclojure.lang.BigInt\n```\n\nThere are also smaller numbers.\n\n```clojure\nuser=\u003e (type (int 0))\njava.lang.Integer\nuser=\u003e (type (short 0))\njava.lang.Short\nuser=\u003e (type (byte 0))\njava.lang.Byte\n```\n\nIntegers are half the size of Longs; they store values in 32 bits. Shorts are\n16 bits, and Bytes are 8. That means their biggest values are 2^31-1, 2^15-1, and\n2^7-1, respectively.\n\n```clojure\nuser=\u003e Integer/MAX_VALUE\n2147483647\nuser=\u003e Short/MAX_VALUE\n32767\nuser=\u003e Byte/MAX_VALUE\n127\n```\n\n### Fractional numbers\n\nTo represent numbers *between* integers, we often use floating-point numbers,\nwhich can represent small numbers with fine precision, and large numbers with\ncoarse precision. Floats use 32 bits, and Doubles use 64. Doubles are the\ndefault in Clojure.\n\n```clojure\nuser=\u003e (type 1.23)\njava.lang.Double\nuser=\u003e (type (float 1.23))\njava.lang.Float\n```\n\nFloating point math is\n[complicated](http://en.wikipedia.org/wiki/Floating_point), and we won’t get\nbogged down in the details just yet. The important thing to know is floats and\ndoubles are *approximations*. There are limits to their correctness:\n\n```clojure\nuser=\u003e 0.99999999999999999\n1.0\n```\n\nTo represent fractions exactly, we can use the *ratio* type:\n\n```clojure\nuser=\u003e (type 1/3)\nclojure.lang.Ratio\n```\n\n### Mathematical operations\n\nThe exact behavior of mathematical operations in Clojure depends on their\ntypes. In general, though, Clojure aims to *preserve* information. Adding two\nlongs returns a long; adding a double and a long returns a double.\n\n```clojure\nuser=\u003e (+ 1 2)\n3\nuser=\u003e (+ 1 2.0)\n3.0\n```\n\n`3` and `3.0` are *not* the same number; one is a long, and the other a double. But\nfor most purposes, they’re equivalent, and Clojure will tell you so:\n\n```clojure\nuser=\u003e (= 3 3.0)\nfalse\nuser=\u003e (== 3 3.0)\ntrue\n```\n\n`=` asks whether all the things that follow are equal. Since floats are\napproximations, `=` considers them different from integers. `==` also compares\nthings, but a little more loosely: it considers integers equivalent to their\nfloating-point representations.\n\nWe can also subtract with `-`, multiply with `*`, and divide with `/`.\n\n```clojure\nuser=\u003e (- 3 1)\n2\nuser=\u003e (* 1.5 3)\n4.5\nuser=\u003e (/ 1 2)\n1/2\n```\n\nPutting the verb first in each list allows us to add or multiply more than one\nnumber in the same step:\n\n```clojure\nuser=\u003e (+ 1 2 3)\n6\nuser=\u003e (* 2 3 1/5)\n6/5\n```\n\nSubtraction with more than 2 numbers subtracts all later numbers from the\n*first*. Division divides the first number by all the rest.\n\n```clojure\nuser=\u003e (- 5 1 1 1)\n2\nuser=\u003e (/ 24 2 3)\n4\n```\n\nBy extension, we can define useful interpretations for numeric operations with\njust a *single* number:\n\n```clojure\nuser=\u003e (+ 2)\n2\nuser=\u003e (- 2)\n-2\nuser=\u003e (* 4)\n4\nuser=\u003e (/ 4)\n1/4\n```\n\nWe can also add or multiply a list of no numbers at all, obtaining the additive\nand multiplicative identities, respectively. This might seem odd, especially\ncoming from other languages, but we’ll see later that these generalizations\nmake it easier to reason about higher-level numeric operations.\n\n```clojure\nuser=\u003e (+)\n0\nuser=\u003e (*)\n1\n```\n\nOften, we want to ask which number is bigger, or if one number falls between\ntwo others. `\u003c=` means “less than or equal to”, and asserts that all following\nvalues are in order from smallest to biggest.\n\n```clojure\nuser=\u003e (\u003c= 1 2 3)\ntrue\nuser=\u003e (\u003c= 1 3 2)\nfalse\n```\n\n`\u003c` means “strictly less than”, and works just like `\u003c=`, except that no two values\nmay be equal.\n\n```clojure\nuser=\u003e (\u003c= 1 1 2)\ntrue\nuser=\u003e (\u003c 1 1 2)\nfalse\n```\n\nTheir friends `\u003e` and `\u003e=` mean “greater than” and “greater than or equal to”,\nrespectively, and assert that numbers are in descending order.\n\n```clojure\nuser=\u003e (\u003e 3 2 1)\ntrue\nuser=\u003e (\u003e 1 2 3)\nfalse\n```\n\nAlso commonly used are `inc` and `dec`, which add and subtract one to a number,\nrespectively:\n\n```clojure\nuser=\u003e (inc 5)\n6\nuser=\u003e (dec 5)\n4\n```\n\nOne final note: equality tests can take more than 2 numbers as well.\n\n```clojure\nuser=\u003e (= 2 2 2)\ntrue\nuser=\u003e (= 2 2 3)\nfalse\n```\n\n### Strings\n\nWe saw that strings are text, surrounded by double quotes, like `\"foo\"`. Strings\nin Clojure are, like Longs, Doubles, and company, backed by a Java type:\n\n```clojure\nuser=\u003e (type \"cat\")\njava.lang.String\n```\n\nWe can make almost *anything* into a string with `str`. Strings, symbols, numbers,\nbooleans; every value in Clojure has a string representation. Note that `nil`’s\nstring representation is `\"\"`; an empty string.\n\n```clojure\nuser=\u003e (str \"cat\")\n\"cat\"\nuser=\u003e (str 'cat)\n\"cat\"\nuser=\u003e (str 1)\n\"1\"\nuser=\u003e (str true)\n\"true\"\nuser=\u003e (str '(1 2 3))\n\"(1 2 3)\"\nuser=\u003e (str nil)\n\"\"\n```\n\n`str` can also *combine* things together into a single string, which we call\n“concatenation”.\n\n```clojure\nuser=\u003e (str \"meow \" 3 \" times\")\n\"meow 3 times\"\n```\n\nTo look for patterns in text, we can use a [regular\nexpression](http://www.regular-expressions.info/tutorial.html), which is a tiny\nlanguage for describing particular arrangements of text. `re-find` and `re-matches`\nlook for occurrences of a regular expression in a string. To find a cat:\n\n```clojure\nuser=\u003e (re-find #\"cat\" \"mystic cat mouse\")\n\"cat\"\nuser=\u003e (re-find #\"cat\" \"only dogs here\")\nnil\n```\n\nThat `#\"...\"` is Clojure’s way of writing a regular expression.\n\nWith `re-matches`, you can extract particular parts of a string which match an\nexpression. Here we find two strings, separated by a `:`. The parentheses mean\nthat the regular expression should *capture* that part of the match. We get back\na list containing the part of the string that matched the first parentheses,\nfollowed by the part that matched the second parentheses.\n\n```clojure\nuser=\u003e (rest (re-matches #\"(.+):(.+)\" \"mouse:treat\"))\n(\"mouse\" \"treat\")\n```\n\nRegular expressions are a powerful tool for searching and matching text,\nespecially when working with data files. Since regexes work the same in most\nlanguages, you can use any guide online to learn more. It’s not something you\nhave to master right away; just learn specific tricks as you find you need\nthem. For a deeper guide, try Fitzgerald’s [Introducing Regular\nExpressions](http://shop.oreilly.com/product/0636920012337.do).\n\n### Booleans and logic\n\nEverything in Clojure has a sort of charge, a truth value, sometimes called\n“truthiness”. `true` is positive and `false` is negative. `nil` is negative, too.\n\n```clojure\nuser=\u003e (boolean true)\ntrue\nuser=\u003e (boolean false)\nfalse\nuser=\u003e (boolean nil)\nfalse\n```\n\nEvery other value in Clojure is positive.\n\n```clojure\nuser=\u003e (boolean 0)\ntrue\nuser=\u003e (boolean 1)\ntrue\nuser=\u003e (boolean \"hi there\")\ntrue\nuser=\u003e (boolean str)\ntrue\n```\n\nIf you’re coming from a C-inspired language, where 0 is considered false, this\nmight be a bit surprising. Likewise, in much of POSIX, 0 is considered success\nand nonzero values are failures. Lisp allows no such confusion: the only\nnegative values are `false` and `nil`.\n\nWe can reason about truth values using `and`, `or`, and `not`. and returns the first\nnegative value, or the last value if all are truthy.\n\n```clojure\nuser=\u003e (and true false true)\nfalse\nuser=\u003e (and true true true)\ntrue\nuser=\u003e (and 1 2 3)\n3\n```\n\nSimilarly, `or` returns the first positive value.\n\n```clojure\nuser=\u003e (or false 2 3)\n2\nuser=\u003e (or false nil)\nnil\n```\n\nAnd `not` inverts the logical sense of a value:\n\n```clojure\nuser=\u003e (not 2)\nfalse\nuser=\u003e (not nil)\ntrue\n```\n\nWe’ll learn more about Boolean logic when we start talking about *control flow*;\nthe way we alter evaluation of a program and express ideas like “if I’m a cat,\nthen meow incessantly”.\n\n### Symbols\n\nWe saw symbols in the previous chapter; they’re bare strings of characters,\nlike `foo` or `+.`\n\n```clojure\nuser=\u003e (class 'str)\nclojure.lang.Symbol\n```\n\nSymbols can have either short or full names. The short name is used to refer to\nthings locally. The *fully qualified* name is used to refer unambiguously to a\nsymbol from anywhere. If I were a symbol, my name would be “Kyle”, and my full\nname “Kyle Kingsbury.”\n\nSymbol names are separated with a `/`. For instance, the symbol `str` is also\npresent in a family called `clojure.core`; the corresponding full name is\n`clojure.core/str`.\n\n```clojure\nuser=\u003e (= str clojure.core/str)\ntrue\nuser=\u003e (name 'clojure.core/str)\n\"str\"\n```\n\nWhen we talked about the maximum size of an integer, that was a fully-qualified\nsymbol, too.\n\n```clojure\n(type 'Integer/MAX_VALUE)\nclojure.lang.Symbol\n```\n\nThe job of symbols is to *refer* to things, to *point* to other values. When\nevaluating a program, symbols are looked up and replaced by their corresponding\nvalues. That’s not the only use of symbols, but it’s the most common.\n\n### Keywords\n\nClosely related to symbols and strings are *keywords*, which begin with a `:`.\nKeywords are like strings in that they’re made up of text, but are specifically\nintended for use as *labels* or *identifiers*. These aren’t labels in the sense of\nsymbols: keywords aren’t replaced by any other value. They’re just names, by\nthemselves.\n\n```clojure\nuser=\u003e (type :cat)\nclojure.lang.Keyword\nuser=\u003e (str :cat)\n\":cat\"\nuser=\u003e (name :cat)\n\"cat\"\n```\n\nAs labels, keywords are most useful when paired with other values in a\ncollection, like a *map*. Keywords can also be used as verbs to *look up specific\nvalues* in other data types. We’ll learn more about keywords shortly.\n\n### Lists\n\nA collection is a group of values. It’s a *container* which provides some\nstructure, some framework, for the things that it holds. We say that a\ncollection contains *elements*, or *members*. We saw one kind of collection–a\nlist–in the previous chapter.\n\n```clojure\nuser=\u003e '(1 2 3)\n(1 2 3)\nuser=\u003e (type '(1 2 3))\nclojure.lang.PersistentList\n```\n\nRemember, we *quote* lists with a `'` to prevent them from being evaluated. You can\nalso construct a list using `list`:\n\n```clojure\nuser=\u003e (list 1 2 3)\n(1 2 3)\n```\n\nLists are comparable just like every other value:\n\n```clojure\nuser=\u003e (= (list 1 2) (list 1 2))\ntrue\n```\n\nYou can modify a list by `conj`oining an element onto it:\n\n```clojure\nuser=\u003e (conj '(1 2 3) 4)\n(4 1 2 3)\n```\n\nWe added 4 to the list–but it appeared at the *front*. Why? Internally, lists are\nstored as a *chain* of values: each link in the chain is a tiny box which holds\nthe value and a connection to the next link. This data structure, called a\nlinked list, offers immediate access to the first element.\n\n```clojure\nuser=\u003e (first (list 1 2 3))\n1\n```\n\nBut getting to the second element requires an extra hop down the chain\n\n```clojure\nuser=\u003e (second (list 1 2 3))\n2\n```\n\nand the third element a hop after that, and so on.\n\n```clojure\nuser=\u003e (nth (list 1 2 3) 2)\n3\n```\n\n`nth` gets the element of an ordered collection at a particular *index*. The first\nelement is index 0, the second is index 1, and so on.\n\nThis means that lists are well-suited for small collections, or collections\nwhich are read in linear order, but are slow when you want to get arbitrary\nelements from later in the list. For fast access to every element, we use a\n*vector*.\n\n### Vectors\n\nVectors are surrounded by square brackets, just like lists are surrounded by\nparentheses. Because vectors *aren’t* evaluated like lists are, there’s no need\nto quote them:\n\n```clojure\nuser=\u003e [1 2 3]\n[1 2 3]\nuser=\u003e (type [1 2 3])\nclojure.lang.PersistentVector\n```\n\nYou can also create vectors with `vector`, or change other structures into\nvectors with `vec`:\n\n```clojure\nuser=\u003e (vector 1 2 3)\n[1 2 3]\nuser=\u003e (vec (list 1 2 3))\n[1 2 3]\n```\n\n`conj` on a vector adds to the *end*, not the *start*:\n\n```clojure\nuser=\u003e (conj [1 2 3] 4)\n[1 2 3 4]\n```\n\nOur friends `first`, `second`, and `nth` work here too; but unlike lists, nth is *fast*\non vectors. That’s because internally, vectors are represented as a very broad\ntree of elements, where each part of the tree branches into 32 smaller trees.\nEven very large vectors are only a few layers deep, which means getting to\nelements only takes a few hops.\n\nIn addition to `first`, you’ll often want to get the *remaining* elements in a\ncollection. There are two ways to do this:\n\n```clojure\nuser=\u003e (rest [1 2 3])\n(2 3)\nuser=\u003e (next [1 2 3])\n(2 3)\n```\n\n`rest` and `next` both return “everything but the first element”. They differ only\nby what happens when there are no remaining elements:\n\n```clojure\nuser=\u003e (rest [1])\n()\nuser=\u003e (next [1])\nnil\n```\n\nrest returns logical true, next returns logical false. Each has their uses, but\nin almost every case they’re equivalent–I interchange them freely.\n\nWe can get the final element of any collection with `last`:\n\n```clojure\nuser=\u003e (last [1 2 3])\n3\n```\n\nAnd figure out how big the vector is with `count`:\n\n```clojure\nuser=\u003e (count [1 2 3])\n3\n```\n\nBecause vectors are intended for looking up elements by index, we can also use\nthem directly as *verbs*:\n\n```\nuser=\u003e ([:a :b :c] 1)\n:b\n```\n\nSo we took the vector containing three keywords, and asked “What’s the element\nat index 1?” Lisp, like most (but not all!) modern languages, counts up from\n*zero*, not one. Index 0 is the first element, index 1 is the second element, and\nso on. In this vector, finding the element at index 1 evaluates to `:b`.\n\nFinally, note that vectors and lists containing the same elements are\nconsidered equal in Clojure:\n\n```clojure\nuser=\u003e (= '(1 2 3) [1 2 3])\ntrue\n```\n\nIn almost all contexts, you can consider vectors, lists, and other sequences as\ninterchangeable. They only differ in their performance characteristics, and in\na few data-structure-specific operations.\n\n### Sets\n\nSometimes you want an unordered collection of values; especially when you plan\nto ask questions like “does the collection have the number 3 in it?” Clojure,\nlike most languages, calls these collections sets.\n\n```clojure\nuser=\u003e #{:a :b :c}\n#{:a :c :b}\n```\n\nSets are surrounded by `#{...}`. Notice that though we gave the elements `:a`, `:b`,\nand `:c`, they came out in a different order. In general, the order of sets can\nshift at any time. If you want a particular order, you can ask for it as a list\nor vector:\n\n```clojure\nuser=\u003e (vec #{:a :b :c})\n[:a :c :b]\n```\n\nOr ask for the elements in sorted order:\n\n```clojure\n(sort #{:a :b :c})\n(:a :b :c)\n```\n\n`conj` on a set adds an element:\n\n```clojure\nuser=\u003e (conj #{:a :b :c} :d)\n#{:a :c :b :d}\nuser=\u003e (conj #{:a :b :c} :a)\n#{:a :c :b}\n```\n\nSets never contain an element more than once, so `conj`ing an element which is\nalready present does nothing. Conversely, one removes elements with `disj`:\n\n```clojure\nuser=\u003e (disj #{\"hornet\" \"hummingbird\"} \"hummingbird\")\n#{\"hornet\"}\n````\n\nThe most common operation with a set is to check whether something is inside\nit. For this we use `contains`?.\n\n```clojure\nuser=\u003e (contains? #{1 2 3} 3)\ntrue\nuser=\u003e (contains? #{1 2 3} 5)\nfalse\n```\n\nLike vectors, you can use the set *itself* as a verb. Unlike `contains?`, this\nexpression returns the element itself (if it was present), or `nil`.\n\n```clojure\nuser=\u003e (#{1 2 3} 3)\n3\nuser=\u003e (#{1 2 3} 4)\nnil\n```\n\nYou can make a set out of any other collection with `set`.\n\n```clojure\nuser=\u003e (set [:a :b :c])\n#{:a :c :b}\n```\n\n### Maps\n\nThe last collection on our tour is the *map*: a data structure which associates\n*keys* with *values*. In a dictionary, the keys are words and the definitions are\nthe values. In a library, keys are call signs, and the books are values. Maps\nare indexes for looking things up, and for representing different pieces of\nnamed information together. Here’s a cat:\n\n```clojure\nuser=\u003e {:name \"mittens\" :weight 9 :color \"black\"}\n{:weight 9, :name \"mittens\", :color \"black\"}\n```\n\nMaps are surrounded by braces `{...}`, filled by alternating keys and values. In\nthis map, the three keys are `:name`, `:color`, and `:weight`, and their values are\n`\"mittens\"`, `\"black\"`, and 9, respectively. We can look up the corresponding value\nfor a key with `get`:\n\n```clojure\nuser=\u003e (get {\"cat\" \"meow\" \"dog\" \"woof\"} \"cat\")\n\"meow\"\nuser=\u003e (get {:a 1 :b 2} :c)\nnil\n```\n\n`get` can also take a *default* value to return instead of nil, if the key doesn’t\nexist in that map.\n\n```clojure\nuser=\u003e (get {:glinda :good} :wicked :not-here)\n:not-here\n```\n\nSince lookups are so important for maps, we can use a map as a verb directly:\n\n```clojure\nuser=\u003e ({\"amlodipine\" 12 \"ibuprofen\" 50} \"ibuprofen\")\n50\n```\n\nAnd conversely, keywords can also be used as verbs, which look themselves up in\nmaps:\n\n```clojure\nuser=\u003e (:raccoon {:weasel \"queen\" :raccoon \"king\"})\n\"king\"\n```\n\nYou can add a value for a given key to a map with `assoc`.\n\n```clojure\nuser=\u003e (assoc {:bolts 1088} :camshafts 3)\n{:camshafts 3 :bolts 1088}\nuser=\u003e (assoc {:camshafts 3} :camshafts 2)\n{:camshafts 2}\n```\n\nAssoc adds keys if they aren’t present, and *replaces* values if they’re already\nthere. If you associate a value onto `nil`, it creates a new map.\n\n```clojure\nuser=\u003e (assoc nil 5 2)\n{5 2}\n```\n\nYou can combine maps together using `merge`, which yields a map containing all\nthe elements of all given maps, preferring the values from later ones.\n\n```clojure\nuser=\u003e (merge {:a 1 :b 2} {:b 3 :c 4})\n{:c 4, :a 1, :b 3}\n```\n\nFinally, to remove a value, use `dissoc`.\n\n```clojure\nuser=\u003e (dissoc {:potatoes 5 :mushrooms 2} :mushrooms)\n{:potatoes 5}\n```\n\n### Putting it all together\n\nAll these collections and types can be combined freely. As software engineers,\nwe model the world by creating a particular *representation* of the problem in\nthe program. Having a rich set of values at our disposal allows us to talk\nabout complex problems. We might describe a person:\n\n```clojure\n{:name \"Amelia Earhart\"\n :birth 1897\n :death 1939\n :awards {\"US\"    #{\"Distinguished Flying Cross\" \"National Women's Hall of Fame\"}\n          \"World\" #{\"Altitude record for Autogyro\" \"First to cross Atlantic twice\"}}}\n```\n\nOr a recipe:\n\n```clojure\n{:title \"Chocolate chip cookies\"\n :ingredients {\"flour\"           [(+ 2 1/4) :cup]\n               \"baking soda\"     [1   :teaspoon]\n               \"salt\"            [1   :teaspoon]\n               \"butter\"          [1   :cup]\n               \"sugar\"           [3/4 :cup]\n               \"brown sugar\"     [3/4 :cup]\n               \"vanilla\"         [1   :teaspoon]\n               \"eggs\"            2\n               \"chocolate chips\" [12  :ounce]}}\n```\n\nOr the Gini coefficients of nations, as measured over time:\n\n```\n{\"Afghanistan\" {2008 27.8}\n \"Indonesia\"   {2008 34.1 2010 35.6 2011 38.1}\n \"Uruguay\"     {2008 46.3 2009 46.3 2010 45.3}}\n```\n\nIn Clojure, we *compose* data structures to form more complex values; to talk\nabout bigger ideas. We use operations like `first`, `nth`, `get`, and `contains?` to\nextract specific information from these structures, and modify them using `conj`,\n`disj`, `assoc`, `dissoc`, and so on.\n\nWe started this chapter with a discussion of *types*: groups of similar objects\nwhich obey the same rules. We learned that bigints, longs, ints, shorts, and\nbytes are all integers, that doubles and floats are approximations to decimal\nnumbers, and that ratios represent fractions exactly. We learned the\ndifferences between strings for text, symbols as references, and keywords as\nshort labels. Finally, we learned how to compose, alter, and inspect\ncollections of elements. Armed with the basic nouns of Clojure, we’re ready to\nwrite a broad array of programs.\n\nI’d like to conclude this tour with one last type of value. We’ve inspected\ndozens of types so far–but what what happens when you turn the camera on\nitself?\n\n```clojure\nuser=\u003e (type type)\nclojure.core$type\n```\n\nWhat *is* this `type` thing, exactly? What *are* these verbs we’ve been learning, and\nwhere do they come from? This is the central question of chapter three:\nfunctions.\n\n## Functions\n\nWe left off last chapter with a question: what *are* verbs, anyway? When you\nevaluate `(type :mary-poppins)`, what really happens?\n\n```clojure\nuser=\u003e (type :mary-poppins)\nclojure.lang.Keyword\n```\n\nTo understand how `type` works, we’ll need several new ideas. First, we’ll expand\non the notion of symbols as references to other values. Then we’ll learn about\nfunctions: Clojure’s verbs. Finally, we’ll use the Var system to explore and\nchange the definitions of those functions.\n\n### Let bindings\n\nWe know that symbols are names for things, and that when evaluated, Clojure\nreplaces those symbols with their corresponding values. `+`, for instance, is a\nsymbol which points to the verb `#\u003ccore$_PLUS_ clojure.core$_PLUS_@12992c\u003e`.\n\n```clojure\nuser=\u003e +\n#\u003ccore$_PLUS_ clojure.core$_PLUS_@12992c\u003e\n```\n\nWhen you try to use a symbol which has no defined meaning, Clojure refuses:\n\n```clojure\nuser=\u003e cats\n\nCompilerException java.lang.RuntimeException: Unable to resolve symbol: cats in this context, compiling:(NO_SOURCE_PATH:0:0)\n```\n\nBut we can define a meaning for a symbol within a specific expression, using `let`.\n\n```clojure\nuser=\u003e (let [cats 5] (str \"I have \" cats \" cats.\"))\n\"I have 5 cats.\"\n```\n\nThe `let` expression first takes a vector of *bindings*: alternating symbols and\nvalues that those symbols are *bound* to, within the remainder of the expression.\n“Let the symbol `cats` be 5, and construct a string composed of `\"I have \"`, `cats`,\nand `\" cats\"`.\n\nLet bindings apply only within the let expression itself. They also override\nany existing definitions for symbols at that point in the program. For\ninstance, we can redefine addition to mean subtraction, for the duration of a\n`let`:\n\n```clojure\nuser=\u003e (let [+ -] (+ 2 3))\n-1\n```\n\nBut that definition doesn’t apply outside the let:\n\n```clojure\nuser=\u003e (+ 2 3)\n5\n```\n\nWe can also provide *multiple* bindings. Since Clojure doesn’t care about\nspacing, alignment, or newlines, I’ll write this on multiple lines for clarity.\n\n```clojure\nuser=\u003e (let [person   \"joseph\"\n             num-cats 186]\n         (str person \" has \" num-cats \" cats!\"))\n\"joseph has 186 cats!\"\n```\n\nWhen multiple bindings are given, they are evaluated in order. Later bindings\ncan use previous bindings.\n\n```clojure\nuser=\u003e (let [cats 3\n             legs (* 4 cats)]\n         (str legs \" legs all together\"))\n\"12 legs all together\"\n```\n\nSo fundamentally, `let` defines the meaning of symbols within an expression. When\nClojure evaluates a `let`, it replaces all occurrences of those symbols in the\nrest of the `let` expression with their corresponding values, then evaluates the\nrest of the expression.\n\n### Functions\n\nWe saw in chapter one that Clojure evaluates lists by *substituting* some other\nvalue in their place:\n\n```clojure\nuser=\u003e (inc 1)\n2\n```\n\n`inc` takes any number, and is replaced by that number plus one. That sounds an\nawful lot like a let:\n\n```clojure\nuser=\u003e (let [x 1] (+ x 1))\n2\n```\n\nIf we bound `x` to `5` instead of `1`, this expression would evaluate to `6`. We can\nthink about `inc` like a let expression, but without particular values provided\nfor the symbols.\n\n```clojure\n(let [x] (+ x 1))\n```\n\nWe can’t actually evaluate this program, because there’s no value for `x` yet. It\ncould be 1, or 4, or 1453. We say that `x` is *unbound*, because it has no binding\nto a particular value. This is the nature of the *function*: an expression with\nunbound symbols.\n\n```clojure\nuser=\u003e (fn [x] (+ x 1))\n#\u003cuser$eval293$fn__294 user$eval293$fn__294@663fc37\u003e\n```\n\nDoes the name of that function remind you of anything?\n\n```clojure\nuser=\u003e inc\n#\u003ccore$inc clojure.core$inc@16bc0b3c\u003e\n```\n\nAlmost all verbs in Clojure are functions. Functions represent unrealized\ncomputation: expressions which are not yet evaluated, or incomplete. This\nparticular function works just like `inc`: it’s an expression which has a single\nunbound symbol, `x`. When we *invoke* the function with a particular value, the\nexpressions in the function are evaluated with `x` bound to that value.\n\n```clojure\nuser=\u003e (inc 2)\n3\nuser=\u003e ((fn [x] (+ x 1)) 2)\n3\n```\n\nWe say that `x` is this function’s *argument*, or *parameter*. When Clojure evaluates\n`(inc 2)`, we say that `inc` is *called* with `2`, or that `2` is passed to `inc`. The\nresult of that *function invocation* is the function’s *return value*. We say that\n`(inc 2)` *returns* `3`.\n\nFundamentally, functions describe the relationship between arguments and return\nvalues: given `1`, return `2`. Given `2`, return `3`, and so on. Let bindings describe\na similar relationship, but with a specific set of values for those arguments.\n`let` is evaluated immediately, whereas `fn` is evaluated *later*, when bindings are\nprovided.\n\nThere’s a shorthand for writing functions, too: `#(+ % 1)` is equivalent to `(fn\n[x] (+ x 1))`. `%` takes the place of the first argument to the function. You’ll\nsometime see `%1`, `%2`, etc. used for the first argument, second argument, and so\non.\n\n```clojure\nuser=\u003e (let [burrito #(list \"beans\" % \"cheese\")]\n         (burrito \"carnitas\"))\n(\"beans\" \"carnitas\" \"cheese\")\n```\n\nSince functions exist to *defer* evaluation, there’s no sense in creating and\ninvoking them in the same expression as we’ve done here. What we want is to\ngive *names* to our functions, so they can be recombined in different ways.\n\n```clojure\nuser=\u003e (let [twice (fn [x] (* 2 x))]\n         (+ (twice 1)\n            (twice 3)))\n8\n```\n\nCompare that expression to an equivalent, expanded form:\n\n```clojure\nuser=\u003e (+ (* 2 1)\n          (* 2 3))\n```\n\nThe name `twice` is gone, and in its place is the same sort of computation – `(* 2\nsomething)` – written twice. While we *could* represent our programs as a single\nmassive expression, it’d be impossible to reason about. Instead, we use\nfunctions to compact redundant expressions, by isolating common patterns of\ncomputation. Symbols help us re-use those functions (and other values) in more\nthan one place. By giving the symbols meaningful names, we make it easier to\nreason about the structure of the program as a whole; breaking it up into\nsmaller, understandable parts.\n\nThis is core pursuit of software engineering: organizing expressions. Almost\nevery programming language is in search of the right tools to break apart,\nname, and recombine expressions to solve large problems. In Clojure we’ll see\none particular set of tools for composing programs, but the underlying ideas\nwill transfer to many other languages.\n\n### Vars\n\nWe’ve used `let` to define a symbol within an expression, but what about the\ndefault meanings of `+`, `conj`, and `type`? Are they also `let` bindings? Is the whole\nuniverse one giant `let`?\n\nWell, not exactly. That’s one way to think about default bindings, but it’s\nbrittle. We’d need to wrap our whole program in a new `let` expression every time\nwe wanted to change the meaning of a symbol. And moreover, once a `let` is\ndefined, there’s no way to change it. If we want to redefine symbols for\neveryone–even code that we didn’t write–we need a new construct: a *mutable*\nvariable.\n\n```clojure\nuser=\u003e (def cats 5)\n#'user/cats\nuser=\u003e (type #'user/cats)\nclojure.lang.Var\n````\n\n`def` *defines* a type of value we haven’t seen before: a var. Vars, like symbols,\nare references to other values. When evaluated, a symbol pointing to a var is\nreplaced by the var’s corresponding value:\n\n```clojure\nuser=\u003e user/cats\n5\n```\n\n`def` also *binds* the symbol `cats` (and its globally qualified equivalent\n`user/cats`) to that var.\n\n```clojure\nuser=\u003e user/cats\n5\nuser=\u003e cats\n5\n```\n\nWhen we said in chapter one that `inc`, `list`, and friends were symbols that\npointed to functions, that wasn’t the whole story. The symbol `inc` points to the\nvar `#'inc`, which in turn points to the function `#\u003ccore$inc\nclojure.core$inc@16bc0b3c\u003e`. We can see the intermediate var with `resolve`:\n\n```clojure\nuser=\u003e 'inc\ninc ; the symbol\nuser=\u003e (resolve 'inc)\n#'clojure.core/inc ; the var\nuser=\u003e (eval 'inc)\n#\u003ccore$inc clojure.core$inc@16bc0b3c\u003e ; the value\n```\n\nWhy two layers of indirection? Because unlike the symbol, we can *change* the\nmeaning of a Var for everyone, globally, at any time.\n\n```clojure\nuser=\u003e (def astronauts [])\n#'user/astronauts\nuser=\u003e (count astronauts)\n0\nuser=\u003e (def astronauts [\"Sally Ride\" \"Guy Bluford\"])\n#'user/astronauts\nuser=\u003e (count astronauts)\n2\n```\n\nNotice that `astronauts` had *two* distinct meanings, depending on when we\nevaluated it. After the first `def`, astronauts was an empty vector. After the\nsecond `def`, it had one entry.\n\nIf this seems dangerous, you’re a smart cookie. Redefining names in this way\nchanges the meaning of expressions *everywhere* in a program, without warning.\nExpressions which relied on the value of a Var could suddenly take on new,\npossibly incorrect, meanings. It’s a powerful tool for experimenting at the\nREPL, and for updating a running program, but it can have unexpected\nconsequences. Good Clojurists use `def` to set up a program initially, and only\nchange those definitions with careful thought.\n\nTotally redefining a Var isn’t the only option. There are safer, controlled\nways to change the meaning of a Var within a particular part of a program,\nwhich we’ll explore later.\n\n### Defining functions\n\nArmed with *def*, we’re ready to create our own named functions in Clojure.\n\n```clojure\nuser=\u003e (def half (fn [number] (/ number 2)))\n#'user/half\nuser=\u003e (half 6)\n3\n```\n\nCreating a function and binding it to a var is so common that it has its own\nform: `defn`, short for `def` `fn`.\n\n```clojure\nuser=\u003e (defn half [number] (/ number 2))\n#'user/half\n```\n\nFunctions don’t have to take an argument. We’ve seen functions which take zero\narguments, like `(+)`.\n\n```clojure\nuser=\u003e (defn half [] 1/2)\n#'user/half\nuser=\u003e (half)\n1/2\n```\n\nBut if we try to use our earlier form with one argument, Clojure complains that\nthe *arity* – the number of arguments to the function–is incorrect.\n\n```clojure\nuser=\u003e (half 10)\n\nArityException Wrong number of args (1) passed to: user$half  clojure.lang.AFn.throwArity (AFn.java:437)\n```\n\nTo handle *multiple* arities, functions have an alternate form. Instead of an\nargument vector and a body, one provides a series of lists, each of which\nstarts with an argument vector, followed by the body.\n\n```clojure\nuser=\u003e (defn half\n         ([]  1/2)\n         ([x] (/ x 2)))\nuser=\u003e (half)\n1/2\nuser=\u003e (half 10)\n5\n```\n\nMultiple arguments work just like you expect. Just specify an argument vector\nof two, or three, or however many arguments the function takes.\n\n```clojure\nuser=\u003e (defn add\n         [x y]\n         (+ x y))\n#'user/add\nuser=\u003e (add 1 2)\n3\n```\n\nSome functions can take *any* number of arguments. For that, Clojure provides `\u0026`,\nwhich slurps up all remaining arguments as a list:\n\n```clojure\nuser=\u003e (defn vargs\n         [x y \u0026 more-args]\n         {:x    x\n          :y    y\n          :more more-args})\n#'user/vargs\nuser=\u003e (vargs 1)\n\nArityException Wrong number of args (1) passed to: user$vargs  clojure.lang.AFn.throwArity (AFn.java:437)\nuser=\u003e (vargs 1 2)\n{:x 1, :y 2, :more nil}\nuser=\u003e (vargs 1 2 3 4 5)\n{:x 1, :y 2, :more (3 4 5)}\n```\n\nNote that `x` and `y` are mandatory, though there don’t have to be any remaining\narguments.\n\nTo keep track of what arguments a function takes, why the function exists, and\nwhat it does, we usually include a *docstring*. Docstrings help fill in the\nmissing context around functions, to explain their assumptions, context, and\npurpose to the world.\n\n```clojure\n(defn launch\n  \"Launches a spacecraft into the given orbit by initiating a\n   controlled on-axis burn. Does not automatically stage, but\n   does vector thrust, if the craft supports it.\"\n  [craft target-orbit]\n  \"OK, we don't know how to control spacecraft yet.\")\n```\n\nDocstrings are used to automatically generate documentation for Clojure\nprograms, but you can also access them from the REPL.\n\n```clojure\nuser=\u003e (doc launch)\n-------------------------\nuser/launch\n([craft target-orbit])\n   Launches a spacecraft into the given orbit by initiating a\n   controlled on-axis burn. Does not automatically stage, but\n   does vector thrust, if the craft supports it.\nnil\n```\n\n`doc` tells us the full name of the function, the arguments it accepts, and its\ndocstring. This information comes from the `#'launch` var’s *metadata*, and is\nsaved there by `defn`. We can inspect metadata directly with the `meta` function:\n\n```clojure\n(meta #'launch)\n{:arglists ([craft target-orbit]), :ns #\u003cNamespace user\u003e, :name launch, :column 1, :doc \"Launches a spacecraft into the given orbit.\", :line 1, :file \"NO_SOURCE_PATH\"}\nThere’s some other juicy information in there, like the file the function was\ndefined in and which line and column it started at, but that’s not particularly\nuseful since we’re in the REPL, not a file. However, this *does* hint at a way to\nanswer our motivating question: how does the `type` function work?\n```\n\n### How does type work?\n\nWe know that `type` returns the type of an object:\n\n```clojure\nuser=\u003e (type 2)\njava.lang.long\n```\n\nAnd that `type`, like all functions, is a kind of object with its own unique type:\n\n````clojure\nuser=\u003e type\n#\u003ccore$type clojure.core$type@39bda9b9\u003e\nuser=\u003e (type type)\nclojure.core$type\n```\n\nThis tells us that `type` is a particular *instance*, at memory address `39bda9b9`,\nof the type `clojure.core$type`. `clojure.core`\t is a namespace which defines the\nfundamentals of the Clojure language, and `$type` tells us that it’s named `type`\nin that namespace. None of this is particularly helpful, though. Maybe we can\nfind out more about the `clojure.core$type` by asking what its *supertypes* are:\n\n```clojure\nuser=\u003e (supers (type type))\n#{clojure.lang.AFunction clojure.lang.IMeta java.util.concurrent.Callable clojure.lang.Fn clojure.lang.AFn java.util.Comparator java.lang.Object clojure.lang.RestFn clojure.lang.IObj java.lang.Runnable java.io.Serializable clojure.lang.IFn}\n```\n\nThis is a set of all the types that include `type`. We say that `type` is an\n*instance* of `clojure.lang.AFunction`, or that it *implements* or *extends*\n`java.util.concurrent.Callable`, and so on. Since it’s a member of\n`clojure.lang.IMeta` it has metadata, and since it’s a member of\n`clojure.lang.AFn`, it’s a function. Just to double check, let’s confirm that\n`type` is indeed a function:\n\n```clojure\nuser=\u003e (fn? type)\ntrue\n```\n\nWhat about its documentation?\n\n```clojure\nuser=\u003e (doc type)\n-------------------------\nclojure.core/type\n([x])\n  Returns the :type metadata of x, or its Class if none\nnil\n```\n\nAh, that’s helpful. `type` can take a single argument, which it calls `x`. If it\nhas `:type` metadata, that’s what it returns. Otherwise, it returns the class of\nx. Let’s take a deeper look at `type`‘s metadata for more clues.\n\n```clojure\nuser=\u003e (meta #'type)\n{:ns #\u003cNamespace clojure.core\u003e, :name type, :arglists ([x]), :column 1, :added \"1.0\", :static true, :doc \"Returns the :type metadata of x, or its Class if none\", :line 3109, :file \"clojure/core.clj\"}\n````\n\nLook at that! This function was first added to Clojure in version 1.0, and is\ndefined in the file `clojure/core.clj`, on line 3109. We could go dig up the\nClojure source code and read its definition there–or we could ask Clojure to do\nit for us:\n\n```clojure\nuser=\u003e (source type)\n(defn type \n  \"Returns the :type metadata of x, or its Class if none\"\n  {:added \"1.0\"\n   :static true}\n  [x]\n  (or (get (meta x) :type) (class x)))\nnil\n```\n\nAha! Here, at last, is how `type` works. It’s a function which takes a single\nargument `x`, and returns either `:type` from its metadata, or `(class x)`.\n\nWe can delve into any function in Clojure using these tools:\n\n```clojure\nuser=\u003e (source +)\n(defn +\n  \"Returns the sum of nums. (+) returns 0. Does not auto-promote\n  longs, will throw on overflow. See also: +'\"\n  {:inline (nary-inline 'add 'unchecked_add)\n   :inline-arities \u003e1?\n   :added \"1.2\"}\n  ([] 0)\n  ([x] (cast Number x))\n  ([x y] (. clojure.lang.Numbers (add x y)))\n  ([x y \u0026 more]\n     (reduce1 + (+ x y) more)))\nnil\n```\n\nAlmost every function in a programming language is made up of other, simpler\nfunctions. `+`, for instance, is defined in terms of `cast`, `add`, and `reduce1`.\nSometimes functions are defined in terms of themselves. `+` uses itself twice in\nthis definition; a technique called *recursion*.\n\nAt the bottom, though, are certain fundamental constructs below which you can\ngo no further. Core axioms of the language. Lisp calls these \"special forms”.\n`def` and `let` are special forms (well–almost: `let` is a thin wrapper around `let*`,\nwhich is a special form) in Clojure. These forms are defined by the core\nimplementation of the language, and are not reducible to other Clojure\nexpressions.\n\n```clojure\nuser=\u003e (source def)\nSource not found\n```\n\nSome Lisps are written *entirely* in terms of a few special forms, but Clojure is\nmuch less pure. Many functions bottom out in Java functions and types, or, for\nCLJS, in terms of Javascript. Any time you see an expression like `(.\nclojure.lang.Numbers (add x y))`, there’s Java code underneath. Below Java lies\nthe JVM, which might be written in C or C++, depending on which one you use.\nAnd underneath C and C++ lie more libraries, the operating system, assembler,\nmicrocode, registers, and ultimately, electrons flowing through silicon.\n\nA well-designed language *isolates* you from details you don’t need to worry\nabout, like which logic gates or registers to use, and lets you focus on the\ntask at hand. Good languages also need to allow escape hatches for performance\nor access to dangerous functionality, as we saw with Vars. You can write entire\nprograms entirely in terms of Clojure, but sometimes, for performance or to use\ntools from other languages, you’ll rely on Java. The Clojure code is easy to\nexplore with `doc` and `source`, but Java can be more opaque–I usually rely on the\njava source files and online documentation.\n\n### Review\n\nWe’ve seen how `let` associates names with values in a particular expression, and\nhow Vars allow for *mutable* bindings which apply universally. and whose\ndefinitions can change over time. We learned that Clojure verbs are functions,\nwhich express the general shape of an expression but with certain values\n*unbound*. Invoking a function *binds* those variables to specific values, allowing\nevaluation of the function to proceed.\n\nFunctions *decompose* programs into simpler pieces, expressed in terms of one\nanother. Short, meaningful names help us understand what those functions (and\nother values) mean.\n\nFinally, we learned how to introspect Clojure functions with `doc` and\n`source`, and saw the definition of some basic Clojure functions. The [Clojure\ncheatsheet](http://clojure.org/cheatsheet) gives a comprehensive list of the\ncore functions in the language, and is a great starting point when you have to\nsolve a problem but don’t know what functions to use.\n\nWe’ll see a broad swath of those functions in Chapter 4: Sequences.\n\n*My thanks to Zach Tellman, Kelly Sommers, and Michael R Bernstein for reviewing\ndrafts of this chapter.*\n\n## Sequences\n\nIn Chapter 3, we discovered functions as a way to abstract expressions; to\nrephrase a particular computation with some parts missing. We used functions to\ntransform a single value. But what if we want to apply a function to more than\none value at once?\n\n### What about sequences?\n\nFor example, we know that (inc 2) increments the number 2. What if we wanted to\nincrement every number in the vector [1 2 3], producing [2 3 4]?\n\n```clojure\nuser=\u003e (inc [1 2 3])\nClassCastException clojure.lang.PersistentVector cannot be cast to java.lang.Number  clojure.lang.Numbers.inc (Numbers.java:110)\n```\n\nClearly inc can only work on numbers, not on vectors. We need a different kind\nof tool.\n\n### A direct approach\n\nLet’s think about the problem in concrete terms. We want to increment each of\nthree elements: the first, second, and third. We know how to get an element\nfrom a sequence by using nth, so let’s start with the first number, at index 0:\n\n```clojure\nuser=\u003e (def numbers [1 2 3])\n#'user/numbers\nuser=\u003e (nth numbers 0)\n1\nuser=\u003e (inc (nth numbers 0))\n2\n```\n\nSo there’s the first element incremented. Now we can do the second:\n\n```clojure\nuser=\u003e (inc (nth numbers 1))\n3\nuser=\u003e (inc (nth numbers 2))\n4\n```\n\nAnd it should be straightforward to combine these into a vector…\n\n```clojure\nuser=\u003e [(inc (nth numbers 0)) (inc (nth numbers 1)) (inc (nth numbers 2))]\n[2 3 4]\n```\n\nSuccess! We’ve incremented each of the numbers in the list! How about a list\nwith only two elements?\n\n```clojure\nuser=\u003e (def numbers [1 2])\n#'user/numbers\nuser=\u003e [(inc (nth numbers 0)) (inc (nth numbers 1)) (inc (nth numbers 2))]\n\nIndexOutOfBoundsException   clojure.lang.PersistentVector.arrayFor (PersistentVector.java:107)\n```\n\nShoot. We tried to get the element at index 2, but couldn’t, because numbers\nonly has indices 0 and 1. Clojure calls that “index out of bounds”.\n\nWe could just leave off the third expression in the vector; taking only\nelements 0 and 1. But the problem actually gets much worse, because we’d need\nto make this change every time we wanted to use a different sized vector. And\nwhat of a vector with 1000 elements? We’d need 1000 (inc (nth numbers ...))\nexpressions! Down this path lies madness.\n\nLet’s back up a bit, and try a slightly smaller problem.\n\n### Recursion\n\nWhat if we just incremented the first number in the vector? How would that\nwork? We know that first finds the first element in a sequence, and rest finds\nall the remaining ones.\n\n```clojure\nuser=\u003e (first [1 2 3])\n1\nuser=\u003e (rest [1 2 3])\n(2 3)\n```\n\nSo there’s the pieces we’d need. To glue them back together, we can use a\nfunction called cons, which says “make a list beginning with the first\nargument, followed by all the elements in the second argument”.\n\n```clojure\nuser=\u003e (cons 1 [2])\n(1 2)\nuser=\u003e (cons 1 [2 3])\n(1 2 3)\nuser=\u003e (cons 1 [2 3 4])\n(1 2 3 4)\n```\n\nOK so we can split up a sequence, increment the first part, and join them back\ntogether. Not so hard, right?\n\n```clojure\n(defn inc-first [nums]\n  (cons (inc (first nums))\n        (rest nums)))\nuser=\u003e (inc-first [1 2 3 4])\n(2 2 3 4)\n```\n\nHey, there we go! First element changed. Will it work with any length list?\n\n```clojure\nuser=\u003e (inc-first [5])\n(6)\nuser=\u003e (inc-first [])\n\nNullPointerException   clojure.lang.Numbers.ops (Numbers.java:942)\n```\n\nShoot. We can’t increment the first element of this empty vector, because it\ndoesn’t have a first element.\n\n```clojure\nuser=\u003e (first [])\nnil\nuser=\u003e (inc nil)\n\nNullPointerException   clojure.lang.Numbers.ops (Numbers.java:942)\n```\n\nSo there are really two cases for this function. If there is a first element in\nnums, we’ll increment it as normal. If there’s no such element, we’ll return an\nempty list. To express this kind of conditional behavior, we’ll use a Clojure\nspecial form called if:\n\n```clojure\nuser=\u003e (doc if)\n-------------------------\nif\n  (if test then else?)\nSpecial Form\n  Evaluates test. If not the singular values nil or false,\n  evaluates and yields then, otherwise, evaluates and yields else. If\n  else is not supplied it defaults to nil.\n\n  Please see http://clojure.org/special_forms#if\n```\n\nTo confirm our intuition:\n\n```clojure\nuser=\u003e (if true :a :b)\n:a\nuser=\u003e (if false :a :b)\n:b\n```\n\nSeems straightforward enough.\n\n```clojure\n(defn inc-first [nums]\n  (if (first nums)\n    ; If there's a first number, build a new list with cons\n    (cons (inc (first nums))\n          (rest nums))\n    ; If there's no first number, just return an empty list\n    (list)))\n\nuser=\u003e (inc-first [])\n()\nuser=\u003e (inc-first [1 2 3])\n(2 2 3)\n```\n\nSuccess! Now we can handle both cases: empty sequences, and sequences with\nthings in them. Now how about incrementing that second number? Let’s stare at\nthat code for a bit.\n\n```clojure\n(rest nums)\n```\n\nHang on. That list–(rest nums)–that’s a list of numbers too. What if we… used\nour inc-first function on that list, to increment its first number? Then we’d\nhave incremented both the first and the second element.\n\n```clojure\n(defn inc-more [nums]\n  (if (first nums)\n    (cons (inc (first nums))\n          (inc-more (rest nums)))\n    (list)))\nuser=\u003e (inc-more [1 2 3 4])\n(2 3 4 5)\n```\n\nOdd. That didn’t just increment the first two numbers. It incremented all the\nnumbers. We fell into the complete solution entirely by accident. What happened\nhere?\n\nWell first we… yes, we got the number one, and incremented it. Then we stuck\nthat onto (inc-first [2 3 4]), which got two, and incremented it. Then we stuck\nthat two onto (inc-first [3 4]), which got three, and then we did the same for\nfour. Only that time around, at the very end of the list, (rest [4]) would have\nbeen empty. So when we went to get the first number of the empty list, we took\nthe second branch of the if, and returned the empty list.\n\nHaving reached the bottom of the function calls, so to speak, we zip back up\nthe chain. We can imagine this function turning into a long string of cons\ncalls, like so:\n\n```clojure\n(cons 2 (cons 3 (cons 4 (cons 5 '()))))\n(cons 2 (cons 3 (cons 4 '(5))))\n(cons 2 (cons 3 '(4 5)))\n(cons 2 '(3 4 5))\n'(2 3 4 5)\n```\n\nThis technique is called recursion, and it is a fundamental principle in\nworking with collections, sequences, trees, or graphs… any problem which has\nsmall parts linked together. There are two key elements in a recursive program:\n\n1. Some part of the problem which has a known solution\n2. A relationship which connects one part of the problem to the next\n\nIncrementing the elements of an empty list returns the empty list. This is our\nbase case: the ground to build on. Our inductive case, also called the\nrecurrence relation, is how we broke the problem up into incrementing the first\nnumber in the sequence, and incrementing all the numbers in the rest of the\nsequence. The if expression bound these two cases together into a single\nfunction; a function defined in terms of itself.\n\nOnce the initial step has been taken, every step can be taken.\n\n```clojure\nuser=\u003e (inc-more [1 2 3 4 5 6 7 8 9 10 11 12])\n(2 3 4 5 6 7 8 9 10 11 12 13)\n```\n\nThis is the beauty of a recursive function; folding an unbounded stream of\ncomputation over and over, onto itself, until only a single step remains.\n\n### Generalizing from inc\n\nWe set out to increment every number in a vector, but nothing in our solution\nactually depended on inc. It just as well could have been dec, or str, or\nkeyword. Let’s parameterize our inc-more function to use any transformation of\nits elements:\n\n```clojure\n(defn transform-all [f xs]\n  (if (first xs)\n    (cons (f (first xs))\n          (transform-all f (rest xs)))\n    (list)))\n```\n\nBecause we could be talking about any kind of sequence, not just numbers, we’ve\nnamed the sequence xs, and its first element x. We also take a function f as an\nargument, and that function will be applied to each x in turn. So not only can\nwe increment numbers…\n\n```clojure\nuser=\u003e (transform-all inc [1 2 3 4])\n(2 3 4 5)\n```\n\n…but we can turn strings to keywords…\n\n```clojure\nuser=\u003e (transform-all keyword [\"bell\" \"hooks\"])\n(:bell :hooks)\n…or wrap every element in a list:\n\nuser=\u003e (transform-all list [:codex :book :manuscript])\n((:codex) (:book) (:manuscript))\n```\n\nIn short, this function expresses a sequence in which each element is some\nfunction applied to the corresponding element in the underlying sequence. This\nidea is so important that it has its own name, in mathematics, Clojure, and\nother languages. We call it map.\n\n```clojure\nuser=\u003e (map inc [1 2 3 4])\n(2 3 4 5)\n```\n\nYou might remember maps as a datatype in Clojure, too–they’re dictionaries that\nrelate keys to values.\n\n```clojure\n{:year  1969\n :event \"moon landing\"}\n```\n\nThe function map relates one sequence to another. The type map relates keys to\nvalues. There is a deep symmetry between the two: maps are usually sparse, and\nthe relationships between keys and values may be arbitrarily complex. The map\nfunction, on the other hand, usually expresses the same type of relationship,\napplied to a series of elements in fixed order.\n\n### Building sequences\n\nRecursion can do more than just map. We can use it to expand a single value\ninto a sequence of values, each related by some function. For instance:\n\n```clojure\n(defn expand [f x count]\n  (if (pos? count)\n    (cons x (expand f (f x) (dec count)))))\n```\n\nOur base case is x itself, followed by the sequence beginning with (f x). That\nsequence in turn expands to (f (f x)), and then (f (f (f x))), and so on. Each\ntime we call expand, we count down by one using dec. Once the count is zero,\nthe if returns nil, and evaluation stops. If we start with the number 0 and use\ninc as our function:\n\n```clojure\nuser=\u003e user=\u003e (expand inc 0 10)\n(0 1 2 3 4 5 6 7 8 9)\n```\n\nClojure has a more general form of this function, called iterate.\n\n```clojure\nuser=\u003e (take 10 (iterate inc 0))\n(0 1 2 3 4 5 6 7 8 9)\n```\n\nSince this sequence is infinitely long, we’re using take to select only the\nfirst 10 elements. We can construct more complex sequences by using more\ncomplex functions:\n\n```clojure\nuser=\u003e (take 10 (iterate (fn [x] (if (odd? x) (+ 1 x) (/ x 2))) 10))\n(10 5 6 3 4 2 1 2 1 2)\n```\n\nOr build up strings:\n\n```clojure\nuser=\u003e (take 5 (iterate (fn [x] (str x \"o\")) \"y\"))\n(\"y\" \"yo\" \"yoo\" \"yooo\" \"yoooo\")\n```\n\niterate is extremely handy for working with infinite sequences, and has some\npartners in crime. repeat, for instance, constructs a sequence where every\nelement is the same.\n\n```clojure\nuser=\u003e (take 10 (repeat :hi))\n(:hi :hi :hi :hi :hi :hi :hi :hi :hi :hi)\nuser=\u003e (repeat 3 :echo)\n(:echo :echo :echo)\n```\n\nAnd its close relative repeatedly simply calls a function (f) to generate an\ninfinite sequence of values, over and over again, without any relationship\nbetween elements. For an infinite sequence of random numbers:\n\n```clojure\nuser=\u003e (rand)\n0.9002678382322784\nuser=\u003e (rand)\n0.12375594203332863\nuser=\u003e (take 3 (repeatedly rand))\n(0.44442397843046755 0.33668691162169784 0.18244875487846746)\n```\n\nNotice that calling (rand) returns a different number each time. We say that\nrand is an impure function, because it cannot simply be replaced by the same\nvalue every time. It does something different each time it’s called.\n\nThere’s another very handy sequence function specifically for numbers: range,\nwhich generates a sequence of numbers between two points. (range n) gives n\nsuccessive integers starting at 0. (range n m) returns integers from n to m-1.\n(range n m step) returns integers from n to m, but separated by step.\n\n```clojure\nuser=\u003e (range 5)\n(0 1 2 3 4)\nuser=\u003e (range 2 10)\n(2 3 4 5 6 7 8 9)\nuser=\u003e (range 0 100 5)\n(0 5 10 15 20 25 30 35 40 45 50 55 60 65 70 75 80 85 90 95)\n```\n\nTo extend a sequence by repeating it forever, use cycle:\n\n```clojure\nuser=\u003e (take 10 (cycle [1 2 3]))\n(1 2 3 1 2 3 1 2 3 1)\n```\n\n### Transforming sequences\n\nGiven a sequence, we often want to find a related sequence. map, for instance,\napplies a function to each element–but has a few more tricks up its sleeve.\n\n```clojure\nuser=\u003e (map (fn [n vehicle] (str \"I've got \" n \" \" vehicle \"s\"))\n         [0 200 9]\n         [\"car\" \"train\" \"kiteboard\"])\n\n(\"I've got 0 cars\" \"I've got 200 trains\" \"I've got 9 kiteboards\")\n```\n\nIf given multiple sequences, map calls its function with one element from each\nsequence in turn. So the first value will be (f 0 \"car\"), the second (f 200\n\"train\"), and so on. Like a zipper, map folds together corresponding elements\nfrom multiple collections. To sum three vectors, column-wise:\n\n```clojure\nuser=\u003e (map + [1 2 3]\n              [4 5 6]\n              [7 8 9])\n(12 15 18)\n```\n\nIf one sequence is bigger than another, map stops at the end of the smaller\none. We can exploit this to combine finite and infinite sequences. For example,\nto number the elements in a vector:\n\n```clojure\nuser=\u003e (map (fn [index element] (str index \". \" element))\n            (iterate inc 0)\n            [\"erlang\" \"ruby\" \"haskell\"])\n(\"0. erlang\" \"1. ruby\" \"2. haskell\")\n```\n\nTransforming elements together with their indices is so common that Clojure has\na special function for it: map-indexed:\n\n```clojure\nuser=\u003e (map-indexed (fn [index element] (str index \". \" element))\n                    [\"erlang\" \"ruby\" \"haskell\"])\n(\"0. erlang\" \"1. ruby\" \"2. haskell\")\n```\n\nYou can also tack one sequence onto the end of another, like so:\n\n```clojure\nuser=\u003e (concat [1 2 3] [:a :b :c] [4 5 6])\n(1 2 3 :a :b :c 4 5 6)\n```\n\nAnother way to combine two sequences is to riffle them together, using\ninterleave.\n\n```clojure\nuser=\u003e (interleave [:a :b :c] [1 2 3])\n(:a 1 :b 2 :c 3)\n```\n\nAnd if you want to insert a specific element between each successive pair in a\nsequence, try interpose:\n\n```clojure\nuser=\u003e (interpose :and [1 2 3 4])\n(1 :and 2 :and 3 :and 4)\n```\n\nTo reverse a sequence, use reverse.\n\n```clojure\nuser=\u003e (reverse [1 2 3])\n(3 2 1)\nuser=\u003e (reverse \"woolf\")\n(\\f \\l \\o \\o \\w)\n```\n\nStrings are sequences too! Each element of a string is a character, written \\f.\nYou can rejoin those characters into a string with apply str:\n\n```clojure\nuser=\u003e (apply str (reverse \"woolf\"))\n\"floow\"\n…and break strings up into sequences of chars with seq.\n\nuser=\u003e (seq \"sato\")\n(\\s \\a \\t \\o)\n```\n\nTo randomize the order of a sequence, use shuffle.\n\n```clojure\nuser=\u003e (shuffle [1 2 3 4])\n[3 1 2 4]\nuser=\u003e (apply str (shuffle (seq \"abracadabra\")))\n\"acaadabrrab\"\n```\n\n### Subsequences\n\nWe’ve already seen take, which selects the first n elements. There’s also drop,\nwhich removes the first n elements.\n\n```clojure\nuser=\u003e (range 10)\n(0 1 2 3 4 5 6 7 8 9)\nuser=\u003e (take 3 (range 10))\n(0 1 2)\nuser=\u003e (drop 3 (range 10))\n(3 4 5 6 7 8 9)\n```\n\nAnd for slicing apart the other end of the sequence, we have take-last and\ndrop-last:\n\n```clojure\nuser=\u003e (take-last 3 (range 10))\n(7 8 9)\nuser=\u003e (drop-last 3 (range 10))\n(0 1 2 3 4 5 6)\n```\n\ntake-while and drop-while work just like take and drop, but use a function to\ndecide when to cut.\n\n```clojure\nuser=\u003e (take-while pos? [3 2 1 0 -1 -2 10])\n(3 2 1)\n```\n\nIn general, one can cut a sequence in twain by using split-at, and giving it a\nparticular index. There’s also split-with, which uses a function to decide when\nto cut.\n\n```clojure\n(split-at 4 (range 10))\n[(0 1 2 3) (4 5 6 7 8 9)]\nuser=\u003e (split-with number? [1 2 3 :mark 4 5 6 :mark 7])\n[(1 2 3) (:mark 4 5 6 :mark 7)]\n```\n\nNotice that because indexes start at zero, sequence functions tend to have\npredictable numbers of elements. (split-at 4) yields four elements in the first\ncollection, and ensures the second collection begins at index four. (range 10)\nhas ten elements, corresponding to the first ten indices in a sequence. (range\n3 5) has two (since 5 - 3 is two) elements. These choices simplify the\ndefinition of recursive functions as well.\n\nWe can select particular elements from a sequence by applying a function. To\nfind all positive numbers in a list, use filter:\n\n```clojure\nuser=\u003e (filter pos? [1 5 -4 -7 3 0])\n(1 5 3)\n```\n\nfilter looks at each element in turn, and includes it in the resulting sequence\nonly if (f element) returns a truthy value. Its complement is remove, which\nonly includes those elements where (f element) is false or nil.\n\n```clojure\nuser=\u003e (remove string? [1 \"turing\" :apple])\n(1 :apple)\n```\n\nFinally, one can group a sequence into chunks using partition, partition-all,\nor partition-by. For instance, one might group alternating values into pairs:\n\n```clojure\nuser=\u003e (partition 2 [:cats 5 :bats 27 :crocodiles 0])\n((:cats 5) (:bats 27) (:crocodiles 0))\n```\n\nOr separate a series of numbers into negative and positive runs:\n\n```clojure\n(user=\u003e (partition-by neg? [1 2 3 2 1 -1 -2 -3 -2 -1 1 2])\n((1 2 3 2 1) (-1 -2 -3 -2 -1) (1 2))\n```\n\n### Collapsing sequences\n\nAfter transforming a sequence, we often want to collapse it in some way; to\nderive some smaller value. For instance, we might want the number of times each\nelement appears in a sequence:\n\n```clojure\nuser=\u003e (frequencies [:meow :mrrrow :meow :meow])\n{:meow 3, :mrrrow 1}\n```\n\nOr to group elements by some function:\n\n```clojure\nuser=\u003e (pprint (group-by :first [{:first \"Li\"    :last \"Zhou\"}\n                                 {:first \"Sarah\" :last \"Lee\"}\n                                 {:first \"Sarah\" :last \"Dunn\"}\n                                 {:first \"Li\"    :last \"O'Toole\"}]))\n{\"Li\"    [{:last \"Zhou\", :first \"Li\"}   {:last \"O'Toole\", :first \"Li\"}],\n \"Sarah\" [{:last \"Lee\", :first \"Sarah\"} {:last \"Dunn\", :first \"Sarah\"}]}\n```\n\nHere we’ve taken a sequence of people with first and last names, and used the\n:first keyword (which can act as a function!) to look up those first names.\ngroup-by used that function to produce a map of first names to lists of\npeople–kind of like an index.\n\nIn general, we want to combine elements together in some way, using a function.\nWhere map treated each element independently, reducing a sequence requires that\nwe bring some information along. The most general way to collapse a sequence is\nreduce.\n\n```clojure\nuser=\u003e (doc reduce)\n-------------------------\nclojure.core/reduce\n([f coll] [f val coll])\n  f should be a function of 2 arguments. If val is not supplied,\n  returns the result of applying f to the first 2 items in coll, then\n  applying f to that result and the 3rd item, etc. If coll contains no\n  items, f must accept no arguments as well, and reduce returns the\n  result of calling f with no arguments.  If coll has only 1 item, it\n  is returned and f is not called.  If val is supplied, returns the\n  result of applying f to val and the first item in coll, then\n  applying f to that result and the 2nd item, etc. If coll contains no\n  items, returns val and f is not called.\n```\n\nThat’s a little complicated, so we’ll start small. We need a function, f, which\ncombines successive elements of the sequence. (f state element) will return the\nstate for the next invocation of f. As f moves along the sequence, it carries\nsome changing state with it. The final state is the return value of reduce.\n\n```clojure\nuser=\u003e (reduce + [1 2 3 4])\n10\n```\n\nreduce begins by calling (+ 1 2), which yields the state 3. Then it calls (+ 3\n3), which yields 6. Then (+ 6 4), which returns 10. We’ve taken a function over\ntwo elements, and used it to combine all the elements. Mathematically, we could\nwrite:\n\n```clojure\n1 + 2 + 3 + 4\n    3 + 3 + 4\n        6 + 4\n           10\n```\n\nSo another way to look at reduce is like sticking a function between each pair\nof elements. To see the reducing process in action, we can use reductions,\nwhich returns a sequence of all the intermediate states.\n\n```clojure\nuser=\u003e (reductions + [1 2 3 4])\n(1 3 6 10)\n```\n\nOftentimes we include a default state to start with. For instance, we could\nstart with an empty set, and add each element to it as we go along:\n\n```clojure\nuser=\u003e (reduce conj #{} [:a :b :b :b :a :a])\n#{:a :b}\n```\n\nReducing elements into a collection has its own name: into. We can conj [key\nvalue] vectors into a map, for instance, or build up a list:\n\n```clojure\nuser=\u003e (into {} [[:a 2] [:b 3]])\n{:a 2, :b 3}\nuser=\u003e (into (list) [1 2 3 4])\n(4 3 2 1)\n```\n\nBecause elements added to a list appear at the beginning, not the end, this\nexpression reverses the sequence. Vectors conj onto the end, so to emit the\nelements in order, using reduce, we might try:\n\n```clojure\nuser=\u003e (reduce conj [] [1 2 3 4 5])\n(reduce conj [] [1 2 3 4 5])\n[1 2 3 4 5]\n```\n\nWhich brings up an interesting thought: this looks an awful lot like map. All\nthat’s missing is some kind of transformation applied to each element.\n\n```clojure\n(defn my-map [f coll]\n  (reduce (fn [output element]\n            (conj output (f element)))\n          []\n          coll))\nuser=\u003e (my-map inc [1 2 3 4])\n[2 3 4 5]\n```\n\nHuh. map is just a special kind of reduce. What about, say, take-while?\n\n```clojure\n(defn my-take-while [f coll]\n  (reduce (fn [out elem]\n            (if (f elem)\n              (conj out elem)\n              (reduced out)))\n          []\n          coll))\n```\n\nWe’re using a special function here, reduced, to indicate that we’ve completed\nour reduction early and can skip the rest of the sequence.\n\n```clojure\nuser=\u003e (my-take-while pos? [2 1 0 -1 0 1 2])\n[2 1]\n```\n\nreduce really is the uberfunction over sequences. Almost any operation on a\nsequence can be expressed in terms of a reduce–though for various reasons, many\nof the Clojure sequence functions are not written this way. For instance,\ntake-while is actually defined like so:\n\n```clojure\nuser=\u003e (source take-while)\n(defn take-while\n  \"Returns a lazy sequence of successive items from coll while\n  (pred item) returns true. pred must be free of side-effects.\"\n  {:added \"1.0\"\n   :static true}\n  [pred coll]\n  (lazy-seq\n   (when-let [s (seq coll)]\n       (when (pred (first s))\n         (cons (first s) (take-while pred (rest s)))))))\n```\n\nThere’s a few new pieces here, but the structure is essentially the same as our\ninitial attempt at writing map. When the predicate matches the first element,\ncons the first element onto take-while, applied to the rest of the sequence.\nThat lazy-seq construct allows Clojure to compute this sequence as required,\ninstead of right away. It defers execution to a later time.\n\nMost of Clojure’s sequence functions are lazy. They don’t do anything until\nneeded. For instance, we can increment every number from zero to infinity:\n\n```clojure\nuser=\u003e (def infseq (map inc (iterate inc 0)))\n#'user/infseq\nuser=\u003e (realized? infseq)\nfalse\n```\n\nThat function returned immediately. Because it hasn’t done any work yet, we say\nthe sequence is unrealized. It doesn’t increment any numbers at all until we\nask for them:\n\n```clojure\nuser=\u003e (take 10 infseq)\n(1 2 3 4 5 6 7 8 9 10)\nuser=\u003e (realized? infseq)\ntrue\n```\n\nLazy sequences also remember their contents, once evaluated, for faster access.\n\n### Putting it all together\n\nWe’ve seen how recursion generalizes a function over one thing into a function\nover many things, and discovered a rich landscape of recursive functions over\nsequences. Now let’s use our knowledge of sequences to solve a more complex\nproblem: find the sum of the products of consecutive pairs of the first 1000\nodd integers.\n\nFirst, we’ll need the integers. We can start with 0, and work our way up to\ninfinity. To save time printing an infinite number of integers, we’ll start\nwith just the first 10.\n\n```clojure\nuser=\u003e (take 10 (iterate inc 0))\n(0 1 2 3 4 5 6 7 8 9)\n```\n\nNow we need to find only the ones which are odd. Remember, filter pares down a\nsequence to only those elements which pass a test.\n\n```clojure\nuser=\u003e (take 10 (filter odd? (iterate inc 0)))\n(1 3 5 7 9 11 13 15 17 19)\n```\n\nFor consecutive pairs, we want to take [1 3 5 7 ...] and find a sequence like\n([1 3] [3 5] [5 7] ...). That sounds like a job for partition:\n\n```clojure\nuser=\u003e (take 3 (partition 2 (filter odd? (iterate inc 0))))\n((1 3) (5 7) (9 11))\n```\n\nNot quite right–this gave us non-overlapping pairs, but we wanted overlapping\nones too. A quick check of (doc partition) reveals the step parameter:\n\n```clojure\nuser=\u003e (take 3 (partition 2 1 (filter odd? (iterate inc 0))))\n((1 3) (3 5) (5 7))\n```\n\nNow we need to find the product for each pair. Given a pair, multiply the two\npieces together… yes, that sounds like map:\n\n```clojure\nuser=\u003e (take 3 (map (fn [pair] (* (first pair) (second pair)))\n                    (partition 2 1 (filter odd? (iterate inc 0)))))\n(3 15 35)\n```\n\nGetting a bit unwieldy, isn’t it? Only one final step: sum all those products.\nWe’ll adjust the take to include the first 1000, not the first 3, elements.\n\n```clojure\nuser=\u003e (reduce +\n               (take 1000\n                     (map (fn [pair] (* (first pair) (second pair)))\n                          (partition 2 1\n                                    (filter odd?\n                                            (iterate inc 0)))))\n1335333000\n```\n\nThe sum of the first thousand products of consecutive pairs of the odd integers\nstarting at 0. See how each part leads to the next? This expression looks a lot\nlike the way we phrased the problem in English–but both English and Lisp\nexpressions are sort of backwards, in a way. The part that happens first\nappears deepest, last, in the expression. In a chain of reasoning like this,\nit’d be nicer to write it in order.\n\n```clojure\nuser=\u003e (-\u003e\u003e 0\n            (iterate inc)\n            (filter odd?)\n            (partition 2 1)\n            (map (fn [pair]\n                   (* (first pair) (second pair))))\n            (take 1000)\n            (reduce +))\n1335333000\n```\n\nMuch easier to read: now everything flows in order, from top to bottom, and\nwe’ve flattened out the deeply nested expressions into a single level. This is\nhow object-oriented languages structure their expressions: as a chain of\nfunction invocations, each acting on the previous value.\n\nBut how is this possible? Which expression gets evaluated first? (take 1000)\nisn’t even a valid call–where’s its second argument? How are any of these forms\nevaluated?\n\nWhat kind of arcane function is -\u003e\u003e?\n\nAll these mysteries, and more, in Chapter 5: Macros.\n\n### Problems\n\n1. Write a function to find out if a string is a palindrome–that is, if it\n   looks the same forwards and backwards.\n2. Find the number of ‘c’s in “abracadabra”.\n3. Write your own version of filter.\n4. Find the first 100 prime numbers: 2, 3, 5, 7, 11, 13, 17, ….\n\n## Macros\n\nIn Chapter 1, I asserted that the grammar of Lisp is uniform: every expression\nis a list, beginning with a verb, and followed by some arguments. Evaluation\nproceeds from left to right, and every element of the list must be evaluated\nbefore evaluating the list itself. Yet we just saw, at the end of Sequences, an\nexpression which seemed to violate these rules.\n\nClearly, this is not the whole story.\n\n### Macroexpansion\n\nThere is another phase to evaluating an expression; one which takes place\nbefore the rules we’ve followed so far. That process is called macro-expansion.\nDuring macro-expansion, the code itself is restructured according to some set\nof rules–rules which you, the programmer, can define.\n\n```clojure\n(defmacro ignore\n  \"Cancels the evaluation of an expression, returning nil instead.\"\n  [expr]\n  nil)\nuser=\u003e (ignore (+ 1 2))\nnil\n```\n\ndefmacro looks a lot like defn: it has a name, an optional documentation\nstring, an argument vector, and a body–in this case, just nil. In this case, it\nlooks like it simply ignored the expr (+ 1 2) and returned nil–but it’s\nactually deeper than that. (+ 1 2) was never evaluated at all.\n\n```clojure\nuser=\u003e (def x 1)\n#'user/x\nuser=\u003e x\n1\nuser=\u003e (ignore (def x 2))\nnil\nuser=\u003e x\n1\n```\n\ndef should have defined x to be 2 no matter what–but that never happened. At\nmacroexpansion time, the expression (ignore (+ 1 2)) was replaced by the\nexpression nil, which was then evaluated to nil. Where functions rewrite\nvalues, macros rewrite code.\n\nTo see these different layers in play, let’s try a macro which reverses the\norder of arguments to a function.\n\n```clojure\n(defmacro rev [fun \u0026 args]\n  (cons fun (reverse args)))\n```\n\nThis macro, named rev, takes one mandatory argument: a function. Then it takes\nany number of arguments, which are collected in the list args. It constructs a\nnew list, starting with the function, and followed by the arguments, in reverse\norder.\n\nFirst, we macro-expand:\n\n```clojure\nuser=\u003e (macroexpand '(rev str \"hi\" (+ 1 2)))\n(str (+ 1 2) \"hi\")\n```\n\nSo the rev macro took str as the function, and \"hi\" and (+ 1 2) as the\narguments; then constructed a new list with the same function, but the\narguments reversed. When we evaluate that expression, we get:\n\n```clojure\nuser=\u003e (eval (macroexpand '(rev str \"hi\" (+ 1 2))))\n\"3hi\"\n```\n\nmacroexpand takes an expression and returns that expression with all macros\nexpanded. eval takes an expression and evaluates it. When you type an unquoted\nexpression into the REPL, Clojure macroexpands, then evaluates. Two stages–the\nfirst transforming code, the second transforming values.\n\n### Across languages\n\nSome languages have a metalanguage: a language for extending the language\nitself. In C, for example, macros are implemented by the C preprocessor, which\nhas its own syntax for defining expressions, matching patterns in the source\ncode’s text, and replacing that text with other text. But that preprocessor is\nnot C–it is a separate language entirely, with special limitations. In Clojure,\nthe metalanguage is Clojure itself–the full power of the language is available\nto restructure programs. This is called a procedural macro system. Some Lisps,\nlike Scheme, use a macro system based on templating expressions, and still\nothers use more powerful models like f-expressions–but that’s a discussion for\na later time.\n\nThere is another key difference between Lisp macros and many other macro\nsystems: in Lisp, the macros operate on expressions: the data structure of the\ncode itself. Because Lisp code is written explicitly as a data structure, a\ntree made out of lists, this transformation is natural. You can see the\nstructure of the code, which makes it easy to reason about its transformation.\nIn the C preprocessor, macros operate only on text: there is no understanding\nof the underlying syntax. Even in languages like Scala which have syntactic\nmacros, the fact that the code looks nothing like the syntax tree makes it\ncumbersome to truly restructure expressions.\n\nWhen people say that Lisp’s syntax is “more elegant”, or “more beautiful”, or\n“simpler”, this is part of what they they mean. By choosing to represent the\nprogram directly as a a data structure, we make it much easier to define\ncomplex transformations of code itself.\n\n### Defining new syntax\n\nWhat kind of transformations are best expressed with macros?\n\nMost languages encode special syntactic forms–things like “define a function”,\n“call a function”, “define a local variable”, “if this, then that”, and so on.\nIn Clojure, these are called special forms. if is a special form, for instance.\nIts definition is built into the language core itself; it cannot be reduced\ninto smaller parts.\n\n```clojure\n(if (\u003c 3 x)\n  \"big\"\n  \"small\")\n```\n\nOr in Javascript:\n\n```clojure\nif (3 \u003c x) {\n  return \"big\";\n} else {\n  return \"small\";\n}\n```\n\nIn Javascript, Ruby, and many other languages, these special forms are fixed.\nYou cannot define your own syntax. For instance, one cannot define or in a\nlanguage like JS or Ruby: it must be defined for you by the language author.\n\nIn Clojure, or is just a macro.\n\n```clojure\nuser=\u003e (source or)\n(defmacro or\n  \"Evaluates exprs one at a time, from left to right. If a form\n  returns a logical true value, or returns that value and doesn't\n  evaluate any of the other expressions, otherwise it returns the\n  value of the last expression. (or) returns nil.\"\n  {:added \"1.0\"}\n  ([] nil)\n  ([x] x)\n  ([x \u0026 next]\n      `(let [or# ~x]\n         (if or# or# (or ~@next)))))\nnil\n```\n\nThat ` operator–that’s called syntax-quote. It works just like regular\nquote–preventing evaluation of the following list–but with a twist: we can\nescape the quoting rule and substitute in regularly evaluated expressions using\nunquote (~), and unquote-splice (~@). Think of a syntax-quoted expression like\na template for code, with some parts filled in by evaluated forms.\n\n```clojure\nuser=\u003e (let [x 2] `(inc x))\n(clojure.core/inc user/x)\nuser=\u003e (let [x 2] `(inc ~x))\n(clojure.core/inc 2)\n```\n\nSee the difference? ~x substitutes the value of x, instead of using x as an\nunevaluated symbol. This code is essentially just shorthand for something like\n\n```clojure\nuser=\u003e (let [x 2] (list 'clojure.core/inc x))\n(inc 2)\n```\n\n… where we explicitly constructed a new list with the quoted symbol 'inc and\nthe current value of x. Syntax quote just makes it easier to read the code,\nsince the quoted and expanded expressions have similar shapes.\n\nThe ~@ unquote splice works just like ~, except it explodes a list into\nmultiple expressions in the resulting form:\n\n```clojure\nuser=\u003e `(foo ~[1 2 3])\n(user/foo [1 2 3])\nuser=\u003e `(foo ~@[1 2 3])\n(user/foo 1 2 3)\n```\n\n~@ is particularly useful when a function or macro takes an arbitrary number of\narguments. In the definition of or, it’s used to expand (or a b c) recursively.\n\n```clojure\nuser=\u003e (pprint (macroexpand '(or a b c d)))\n(let*\n [or__3943__auto__ a]\n (if or__3943__auto__ or__3943__auto__ (clojure.core/or b c d)))\n```\n\nWe’re using pprint (for “pretty print”) to make this expression easier to read.\n(or a b c d) is defined in terms of if: if the first element is truthy we\nreturn it; otherwise we evaluate (or b c d) instead, and so on.\n\nThe final piece of the puzzle here is that weirdly named symbol:\nor__3943__auto__. That variable was automatically generated by Clojure, to\nprevent conflicts with an existing variable name. Because macros rewrite code,\nthey have to be careful not to interfere with local variables, or it could get\nvery confusing. Whenever we need a new variable in a macro, we use gensym to\ngenerate a new symbol.\n\n```clojure\nuser=\u003e (gensym \"hi\")\nhi326\nuser=\u003e (gensym \"hi\")\nhi329\nuser=\u003e (gensym \"hi\")\nhi332\n```\n\nEach symbol is different! If we tack on a # to the end of a symbol in a\nsyntax-quoted expression, it’ll be expanded to a particular gensym:\n\n```clojure\nuser=\u003e `(let [x# 2] x#)\n(clojure.core/let [x__339__auto__ 2] x__339__auto__)\n```\n\nNote that you can always escape this safety feature if you want to override\nlocal variables. That’s called symbol capture, or an anaphoric or unhygenic\nmacro. To override local symbols, just use ~'foo instead of foo#.\n\nWith all the pieces on the board, let’s compare the or macro and its expansion:\n\n```clojure\n(defmacro or\n  \"Evaluates exprs one at a time, from left to right. If a form\n  returns a logical true value, or returns that value and doesn't\n  evaluate any of the other expressions, otherwise it returns the\n  value of the last expression. (or) returns nil.\"\n  {:added \"1.0\"}\n  ([] nil)\n  ([x] x)\n  ([x \u0026 next]\n      `(let [or# ~x]\n         (if or# or# (or ~@next)))))\n\nuser=\u003e (pprint (clojure.walk/macroexpand-all\n                 '(or (mossy? stone) (cool? stone) (wet? stone))))\n(let*\n [or__3943__auto__ (mossy? stone)]\n (if\n  or__3943__auto__\n  or__3943__auto__\n  (let*\n   [or__3943__auto__ (cool? stone)]\n   (if or__3943__auto__ or__3943__auto__ (wet? stone)))))\n```\n\nSee how the macro’s syntax-quoted (let ... has the same shape as the resulting\ncode? or# is expanded to a variable named or__3943__auto__, which is bound to\nthe expression (mossy? stone). If that variable is truthy, we return it.\nOtherwise, we (and here’s the recursive part) rebind or__3943__auto__ to (cool?\nstone) and try again. If that fails, we fall back to evaluating (wet?\nstone)–thanks to the base case, the single-argument form of the or macro.\n\n### Control flow\n\nWe’ve seen that or is a macro written in terms of the special form if–and\nbecause of the way the macro is structured, it does not obey the normal\nexecution order. In (or a b c), only a is evaluated first–then, only if it is\nfalse or nil, do we evaluate b. This is called short-circuiting, and it works\nfor and as well.\n\nChanging the order of evaluation in a language is called control flow, and lets\nprograms make decisions based on varying circumstances. We’ve already seen if:\n\n```clojure\nuser=\u003e (if (= 2 2) :a :b)\n:a\n```\n\nif takes a predicate and two expressions, and only evaluates one of them,\ndepending on whether the predicate evaluates to a truthy or falsey value.\nSometimes you want to evaluate more than one expression in order. For this, we\nhave do.\n\n```clojure\nuser=\u003e (if (pos? -5)\n         (prn \"-5 is positive\")\n         (do\n           (prn \"-5 is negative\")\n           (prn \"Who would have thought?\")))\n\"-5 is negative\"\n\"Who would have thought?\"\nnil\n```\n\nprn is a function which has a side effect: it prints a message to the screen,\nand returns nil. We wanted to print two messages, but if only takes a single\nexpression per branch–so in our false branch, we used do to wrap up two prns\ninto a single expression, and evaluate them in order. do returns the value of\nthe final expression, which happens to be nil here.\n\nWhen you only want to take one branch of an if, you can use when:\n\n```clojure\nuser=\u003e (when false\n         (prn :hi)\n         (prn :there))\nnil\nuser=\u003e (when true\n         (prn :hi)\n         (prn :there))\n:hi\n:there\nnil\n```\n\nBecause there is only one path to take, when takes any number of expressions,\nand evaluates them only when the predicate is truthy. If the predicate\nevaluates to nil or false, when does not evaluate its body, and returns nil.\n\nBoth when and if have complementary forms, when-not and if-not, which simply\ninvert the sense of their predicate.\n\n```clojure\nuser=\u003e (when-not (number? \"a string\")\n         :here)\n:here\nuser=\u003e (if-not (vector? (list 1 2 3))\n         :a\n         :b)\n:a\n```\n\nOften, you want to perform some operation, and if it’s truthy, re-use that\nvalue without recomputing it. For this, we have when-let and if-let. These work\njust like when and let combined.\n\n```clojure\nuser=\u003e (when-let [x (+ 1 2 3 4)]\n         (str x))\n\"10\"\nuser=\u003e (when-let [x (first [])]\n         (str x))\nnil\n```\n\nwhile evaluates an expression so long as its predicate is truthy. This is\ngenerally useful only for side effects, like prn or def; things that change the\nstate of the world.\n\n```clojure\nuser=\u003e (def x 0)\n#'user/x\nuser=\u003e (while (\u003c x 5)\n  #_=\u003e   (prn x)\n  #_=\u003e   (def x (inc x)))\n0\n1\n2\n3\n4\nnil\n```\n\ncond (for “conditional”) is like a multiheaded if: it takes any number of\ntest/expression pairs, and tries each test in turn. The first test which\nevaluates truthy causes the following expression to be evaluated; then cond\nreturns that expression’s value.\n\n```clojure\nuser=\u003e (cond\n  #_=\u003e   (= 2 5) :nope\n  #_=\u003e   (= 3 3) :yep\n  #_=\u003e   (= 5 5) :cant-get-here\n  #_=\u003e   :else   :a-default-value)\n:yep\n```\n\nIf you find yourself making several similar decisions based on a value, try\ncondp, for “cond with predicate”. For instance, we might categorize a number\nbased on some ranges:\n\n```clojure\n(defn category\n  \"Determines the Saffir-Simpson category of a hurricane, by wind speed in meters/sec\"\n  [wind-speed]\n  (condp \u003c= wind-speed\n    70 :F5\n    58 :F4\n    49 :F3\n    42 :F2\n       :F1)) ; Default value\nuser=\u003e (category 10)\n:F1\nuser=\u003e (category 50)\n:F3\nuser=\u003e (category 100)\n:F5\n```\n\ncondp generates code which combines the predicate \u003c= with each number, and the\nvalue of wind-speed, like so:\n\n```clojure\n(if (\u003c= 70 wind-speed) :F5\n  (if (\u003c= 58 wind-speed) :F4\n    (if (\u003c= 49 wind-speed) :F3\n      (if (\u003c= 42 wind-speed) :F2\n        :F1))))\n```\n\nSpecialized macros like condp are less commonly used than if or when, but they\nstill play an important role in simplifying repeated code. They clarify the\nmeaning of complex expressions, making them easier to read and maintain.\n\nFinally, there’s case, which works a little bit like a map of keys to\nvalues–only the values are code, to be evaluated. You can think of case like\n(condp = ...), trying to match an expression to a particular branch for which\nit is equal.\n\n```clojure\n(defn with-tax\n  \"Computes the total cost, with tax, of a purchase in the given state.\"\n  [state subtotal]\n  (case state\n    :WA (* 1","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fligurio%2Fclojure-from-the-ground-up","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fligurio%2Fclojure-from-the-ground-up","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fligurio%2Fclojure-from-the-ground-up/lists"}