Every and Any in Clojure

Today we look at a few functions in Clojure that take predicates and look at collections: any?, every?, not-every? and not-any?

any? seems to return true for any argument. According to the docs, it is used for clojure.spec. Maybe when I learn more about spec, that will make sense. You would think a function called “any?” would be useful if you had a collection of numbers, and wanted to know if any of them are odd, or greater than 10, or something like that. Perhaps they could have given it a better name than “any?”

every?, not-any? and not-every? behave as you would expect them to. You can always simulate “intuituve-any?” by calling “not-any?” and then calling “not”.

You’re welcome.

Reduce In Clojure

The last of the Big Three Higher Order Functions in Clojure is reduce. In other languages it is called fold, accumulate, aggregate, compress or inject.

Sometimes reduce is compared to aggregate functions in databases, like average, count, sum, min or max. These functions take multiple values, and produce one value. Some functions in Clojure, like the four main math functions (+, -, * and /) are processed through reduce if they are called with more than two values.

The first parameter to Clojure’s reduce is a function that takes two parameters. There is an optional parameter that is an initial value, and the last argument is the collection you want to process. Reduce takes either the option initial value and the first element of the collection, or the first two elements of the collection, and passes them to the function. The output of the function is then used along with the next element in the collection. Reduce keeps using the output from the previous element and the next element as arguments to the function until the collection is exhausted.

I cannot find it now, but I remember reading somewhere that reduce can be hard to understand because “reduce” is frankly not a good name for it, and there are many functions that do what reduce does. As stated, some of the functions in Clojure (like max, min, and some math functions) call reduce. So you are actually using reduce a lot under the covers.

There is a cartoon about this. A teacher gives a student a few chances to say what is “2 + 3” equal to. The student says it equal to “2 + 3” and it is also equal to “3 + 2”. The student gets an F. The cartoon ends with: “Sad fact: many math teachers do not know the difference between equality and reduction.” I admit I do not either. A lot of the cartoons are about Haskell, which I have no desire to learn.

You’re welcome.

Image from  Aurora Consurgens, a 15th century manuscript housed at Central Library of Zurich. Image from e-Codices. This image is assumed to be allowed under Fair Use.

Focusing On Clojure

I have decided to focus on Clojure going forward.

I think of all the Lisps, Clojure right now has the most momentum. And I got a couple of inquiries about Clojure positions.

I have been going through the Clojure API, inspired by an article called “One Weird Trick To Become a Clojure Expert“. The article advocates going through the API alphabetically. Maybe I should have done that, but I think I might be better off going through a few books.

I know at some point I have to stop learning and start making something. But I think that going through the API might not be the best way. And the two are not mutually exclusive.

One of the books I will go through is the third edition of Programming Clojure. One of the co-authors is Alex Miller, who helps make Clojure at Cognitect. Clojure does things differently than other languages, and if anyone can explain it, it is the people at Cognitect. The same publishing company has a book called Getting Clojure, which is written by Russ Olsen, who also works at Cognitect.

Reading books by Cognitect employees is one way you can get Clojure.

You’re welcome.

The Map Function In Clojure

The next member of the Big Three Higher Order Functions is “map“.

I don’t think “map” is a good name for it because 1. There is a data structure named “map” (which has different names in different languages) and 2. I don’t think it is the most descriptive name for it. “apply-to-every” or “apply-to-all” might be better.

The “map” function takes a function and one or more collections, and applies the function to each member in the collection. In Clojure, if you send multiple collections, they will be concatenated into one output collection.

I think the reason it is called “map” is that you are using a function to map a collection onto another collection.

Clojure also has “mapv” which does the same thing as “map” except that it returns a vector, and “mapcat” which takes functions that take collections as arguments. The functions sent to map and mapv take single arguments (if you send one collection) or multiple args, but not collections.

You’re welcome.

Maps In Clojure

I was planning on looking into Clojure’s map function, the second of the Big Three Higher-Order Functions. But looking over my Clojure API page, I noticed there were a few functions with the word “map” in it that I had not gone over yet that deal with the map data structure.

Just as “map” is a noun and a verb in Clojure, the map data structure goes by different names in different programming languages: associative array, map, dictionary, symbol table, hash, hash table.

Anyway, I have looked at some of these functions earlier, but here are some more functions dealing with maps:

You’re welcome.

Clojure Filter

The first higher-order function in Clojure I will look at is filter. It takes a predicate and a collection. It returns all the members of the collection for which the predicate is true. The docs say that it takes a “predicate”, but that predicate duty is frequently fulfilled by a function.

I tried calling filter with “true” as the predicate, and it did not work. I guess in Clojure (and probably all Lisps), a predicate is just a function that returns a boolean.

Filter is one of the Big Three Higher-Order Functions, the other two being Map and Reduce. This one actually has a name that describes what it does.

Clojure has two versions of filter: filter and filterv. The difference is that filter returns a lazy sequence, and filterv returns a vector.

If filter is called with just the predicate, it will return a transducer. I will cover transducers later.

There are also another “filter” function in the clojure.core.reducers namespace. It takes the same arguments as the core filter, but when I tried it in a REPL I got an error. After looking at the Clojure page on reducers, I think the functions in that namespace only work if you chain them together.

You’re welcome.

Chapter 9 of ‘The Little Schemer’

I finally finished chaper 9 of The Little Schemer. This was about partial functions, total functions, and ended with the applicative-order Y combinator.

Frankly, what I understood in this chapter I did not see the point of, and I am not sure there is much point in the parts I do not understand. I think a total function returns a unique value for every input, and partial functions do not. Some of the functions they described as partial sometimes did not return values. Which to me sounds like a badly-designed function.

Maybe Godel’s incompleteness theorem has seeped into our collective consciousness to such a degree that the idea that some functions cannot be computed seems obvious.

Maybe I am not smart enough to be one of those super high-level math/language theory people. I realize I do not have the inclination to do so. I do not have much interest in conjectures about functions that do not return values. I will have to ask a few people I know who have been through SICP if this is the sort of thing in that book. I will finish The Little Schemer and go on to The Seasoned Schemer in a while.

I went through the part about the Y combinator a second time, and I am not too sure I understand it or see the point. Is there a point? According to some guy named Mike, the point of the Y combinator is:  The Y combinator allows us to define recursive functions in computer languages that do not have built-in support for recursive functions, but that do support first-class functions.

Are there languages that fit that description? I did some googling, and I found a Hacker News discussion about “The Why of Y” on Dreamsongs (an interesting website I hope to explore in depth someday). As one commenter points out, the article goes into the How of Y, but never the Why.

The Seasoned Schemer says you only need to understand the first eight chapters of The Little Schemer to go through TSS. So hopefully I should be fine. I was hoping to get through TLS more quickly. I am more busy at work, and chapters 8 and 9 were a lot harder (and had more concepts that were new to me) than the first seven.

I have not gone through these yet, but here are a few more links I found about total and partial functions:

 

You’re welcome.

Image from World Digital Library, assumed allowed under Fair Use. Image from the Ashburnham Pentateuch, or Tours Pentateuch, a Latin manuscript of the first five books of the Old Testament from the 6th century or 7th century. Its place of origin is unknown.

Update on ‘The Little Schemer’

I am almost through with The Little Schemer. I got through the first seven chapters fairly quickly. There are no exercises per se. They will ask questions, invite you to figure out the answer, and show you. I admit, a few times I peeked, but only after trying to get it myself.

There were a few things in chapter 8 that were mind-bending. One was using higher-order functions for code-reuse.

In chapter 3, the authors introduce a few functions. One is “rember”, which removes an element (or member) from a list:

Another is “insertR”, which inserts a new element to the right of an old element in a list:

The third is “insertL”, which inserts a new element to the left of an old element:

The functions are pretty much identical. In chapter 8, they make a base function, and then make three more to cover the three different requirements.

It works just like the original:

This reminds me of something that Eric Normand showed in Purely Functional, where he puts anonymous functions in the values of a map. I wrote about that in August of 2018.

The truly mind-bending part was the “collectors”. Dark arts, these are.

They define a function that does the usual removing of members. It takes an additional parameter which is a function that does some calculations/manipulations on the resulting list. But in the recursive calls, the function uses inline lambdas to make additional collections.

Here is their explanation from page 140; the function is (multirember&co a lat f), where “a” is an atom, “lat” is a list of atoms, and “f’ is a function: It looks at every atom of the lat to see whether it is eq? to a. Those atoms that are not are collected in one list ls1 ; the others for which the answer is true are collected in a second list ls2 . Finally, it determines the value of (f ls1 ls2 ).

Here is the multirember&co function:

Here is the function we will use in our test:

The second argument is unused in last-friend. So when you use last-friend, it will count how many elements are not equal to the first argument. If it returned the length of y, it would tell us how many times the first argument is in the list.

Here are the tests in Racket:

Later, they use collectors on functions that work on multi-level lists. There is a recursive call within the collector.

I think I understand this, but I am not entirely sure about it. I was able to figure out some of the collector examples as they went along. Truly this is unholy power.

You’re welcome.

Image from Corpus Agrimensorum Romanorum, a 6th century manuscript on land surveying housed at the Herzog August Library in  Wolfenbüttel. According to Wikipedia, “It is one of the few surviving non-literary and non-religious illuminated manuscripts from late antiquity.” This image is assumed to be allowed under Fair Use.

On To The Little Books

I finished the poker program from Chapter 15 of Simply Scheme, and I finished Chapter 24.

I have decided I am willing to let MengSince1996 be the King of Berkeley, and move on to Daniel Friedman’s “Little” books.

The first is “The Little Schemer“. This seems to deal with recursion. The first sequel is “The Seasoned Schemer“. The co-author of these books is Matthias Felleisen, one of the founders of Racket. On his Northeastern University page, he states that “The Seasoned Schemer” deals with higher-order functions, set! and continuations.

Next is “The Reasoned Schemer“. This bridges functional programming and logic programming. I work with a rules engine in my day job. I wonder if that is what this is about.

The next book is “The Little Prover“. According to the book’s page on the MIT Press site, this book “introduces inductive proofs as a way to determine facts about computer programs.” Honestly, I am not too clear what that means at this point.

The most recent book in the series is “The Little Typer“. For this book, Friedman and co-author David Thrane Christiansen made a language for the book using Racket.

I will probably use Racket for all these books instead of straight Scheme because I want to be able to run a tests and not type and re-type function invocations every time I make a change. In order to use tests, I had to require the R6RS packages into a program using “#lang racket/base”. I do not think there is a way to use the Racket unit test libraries in an R6RS program. So there are a lot of prefixes.

I like prefixes before function names. It is a bit more typing, and maybe it is not as clean, but I like to know where everything is coming from. One of the things that I did not like about Rails was there were no import or require statements. Everything was everywhere. That made tutorials look very interesting, but it was frustrating finding documentation for classes if you wanted to see what else the gems could do.

I plan on getting through these faster than I took to get through Simply Scheme.

See also my mentions of these books in a post from a few years ago.

You’re welcome.