Some of these are standard Clojure functions, while others are provided
in the file cs378.clj .
- (first lst )
returns the first item in lst. An item is either an atom
(a simple item such as a number or symbol, i.e. a leaf node) or
balanced parentheses and everything inside, no matter how large.
(first '(a b c)) = a
(first '((a b) (c d)) = (a b)
- (second lst )
returns the second item in lst.
(second '(a b c)) = b
(second '((a b) (c d)) = (c d)
- (rest lst )
returns the rest of lst after the first item. Simply move the
initial left parenthesis past the first item to get the answer.
(rest '(a b c)) = (b c)
(rest '((a b) (c d)) = ((c d))
- (cons item lst )
adds item to the front of lst. Simply move the left parenthesis
of lst to the left of item to get the answer.
(cons 'z '(a b c)) = (z a b c)
(cons '(x y) '((a b) (c d)) = ((x y) (a b) (c d))
- (cons? item )
tests whether item is a cons cell (not empty). This function is
in the file cs378.clj .
(cons? '(a b c)) = true
(cons? nil) = false
(cons? '()) = false
- (empty? lst )
tests whether lst is empty, i.e. either nil or ().
empty? expects a cons/list, nil, or (); other argument types
will cause errors.
(empty? '(a b c)) = false
(empty? nil) = true
(empty? '()) = true
- (symbol? item )
tests whether item is a symbol.
(symbol? 'a) = true
(symbol? 3) = false
(symbol? '(a b c)) = false
- (number? item )
tests whether item is a number.
(number? 3) = true
(number? 3.14) = true
(number? '(a b c)) = false
(number? 'a) = false
- (if test trueval )
(if test trueval falseval )
if evaluates the test, then returns the trueval
or falseval. false and nil are considered
to be false; anything else is considered to be true, including
'().
(if (> 3 2) 'yes 'no) = yes
(if (> 2 3) 'yes 'no) = no
(if 2 'yes 'no) = yes
(if '() 'yes 'no) = yes
(if nil 'yes 'no) = no
- (let [ var value ... ]
code )
let allows the initialization of new variables, which
can save intermediate values and thus reduce the repetition of code.
If there are multiple variable-value pairs in the let, they are
done one at a time in order; this is called let* in some Lisp
dialects.
(let [pair (assocl key lst)]
(if pair
(println (second pair)) ))
- (length lst )
returns the number of items at top level of lst.
(length '(a b c)) = 3
(length '((a b) (c d))) = 2
- (reverse lst )
produces a new version of lst with the top-level elements reversed.
(reverse '(a b c)) = (c b a)
(reverse '((a b) (c d))) = ((c d) (a b))
- (append lst1 lst2 )
returns a new list consisting of a copy of the top-level elements
of lst1 followed by lst2. lst1 is copied, while
lst2 is reused via structure sharing. The big O is
O(length(lst1)). The answer is obtained easily by removing
the parentheses between lst1 and lst2.
(append '(a b c) '(d e)) = (a b c d e)
- (op expr )
returns the operator of an expression expr.
(op '(+ x 3)) = +
- (lhs expr )
returns the left-hand side (first operand) of an expression expr.
(lhs '(+ x 3)) = x
- (rhs expr )
returns the right-hand side (second operand) of an expression
expr.
(rhs '(+ x 3)) = 3
- (member item lst )
returns the remainder of lst starting with item
if it is present, or nil otherwise.
(member 'b '(a b c)) = (b c)
(member 'z '(a b c)) = nil
- (assocl key alist )
searches an association list alist, a list of (key value)
pairs, for an item whose key is as specified. If found, the result is
the (key value) pair, or nil otherwise. Note that the
(key value) list could have multiple value items.
assocl is convenient for small maps; Big O is O(n).
This function is called assoc in most Lisp dialects.
(assocl 'two '((one uno) (two dos) (three tres))) = (two dos)
(assocl 'four '((one uno) (two dos) (three tres))) = nil
- (intersection set1 set2 )
returns a list of items that are present in both set1 and set2;
the order of items is arbitrary.
(intersection '(a b c) '(a c e)) = (a c) or (c a)
- (union set1 set2 )
returns a list of items that are present in either set1 or set2;
the order of items is arbitrary.
(union '(a b c) '(a c e)) = (b a c e)
- (set-difference set1 set2 )
returns a list of items that are present in set1 but not in set2;
the order of items is arbitrary. Note that set2 items do not appear
in the answer.
(set-difference '(a b c) '(a c e)) = (b)
- (map fn lst )
returns a list of results of applying fn to each element of lst.
(map reverse '((a b) (c d))) = ((b a) (d c))
- (fn [ args ] code )
produces an anonymous function, i.e. a function without a name.
This is convenient when a rather trivial function is needed for map.
(map (fn [x] (+ x 2)) '(1 2 3)) = (3 4 5)
- (reduce fn lst )
applies the function fn repeatedly to elements of lst,
returning the result of fn on the whole list.
(reduce * '(1 2 3 4)) = 24
- (do expr ... )
do executes its expressions in order and returns the value
of the last expression. It can be used with side-effect expressions
such as printing.
(let [x 3
y 2]
(do (println "x = " x)
(println "y = " y)
(+ x y)) )
x = 3
y = 2
5
In this case, the lines were printed in order, and do
returned 5.
- (doseq [ item lst
] ... )
doseq executes its code with item bound to successive
elements of lst; it can be used for code with side-effects, such as
printing.
(doseq [item '(a b c)] (println item))
a
b
c
nil
In this case, each item was printed, and do returned nil.
- (some fn lst )
some applies fn to successive elements of lst,
returning the first value that is not false or nil.
If no item is found, some returns nil.
(some (fn [x] (> x 3)) '(2 3 4 5)) = true
(some (fn [x] (> x 3)) '(0 1 2 3)) = nil
Typically, we would like to know not only is there some
but which one is it?; in this case, if or and
can be used to get the desired answer.
(some (fn [x] (if (> x 3) x)) '(2 3 4 5)) = 4
(some (fn [x] (and (> x 3) x)) '(2 3 4 5)) = 4
- (every? fn lst )
every? applies fn to every element of lst in order;
if fn returns something other than false or nil
for all elements, every? returns true.
If fn returns false or nil for any element of
lst, every? quits and returns false.
Note that every? returns true if lst is empty.
(every? (fn [x] (> x 3)) '(5 6 7)) = true
(every? (fn [x] (> x 3)) '(2 3 4 5)) = false
(every? (fn [x] (+ x 1)) '(1 2 3)) = true
(every? number? '()) = true
(every? (fn [x] nil) '(1 2 3)) = false
- (equal tree1 tree2 )
equal returns true if tree1 and tree2
have the same structure and leaf elements that are =.
(equal '(* (+ a b) c) '(* (+ a b) c)) = true
The function = does the same in Clojure, though this is not
the case for other Lisp dialects. equal has the same basic structure
as match.
- (match pattern input )
match tries to match pattern and input to determine
whether input is a version of pattern with appropriate
substitutions for variables (symbols beginning with ?)
in the pattern. The result is an association list of substitutions,
or nil if the match fails. Tree structure and constant parts of
the pattern must match exactly (as in equal). A variable will
match anything, but must do so consistently. The alist value (t t)
is used as a sentinel that is not nil, but has no effect
when used in sublis.
(match '(+ ?x ?y) '(+ a b)) = ((?y b) (?x a) (t t))
(match '(- ?x ?x) '(- (sin theta) (sin theta))) = ((?x (sin theta)) (t t))
(match '(- ?x ?x) '(- (sin theta) (cos theta))) = nil
- (copy-tree tree )
copy-tree makes a copy of tree, using new cons
cells but the same leaf nodes. copy-tree has little use in Clojure,
but has the same structure as subst and sublis.
(copy-tree '(* (+ a b) c)) = (* (+ a b) c)
- (subst new old tree )
This is read "substitute new for old in tree".
subst makes a copy of tree, using new cons
cells but the same leaf nodes; however, any leaf node that is =
to old will be replaced by new.
(subst 'fish 'beef '(beef taco)) = (fish taco)
- (sublis alist tree )
sublis makes a copy of tree, using new cons
cells but the same leaf nodes; however, any leaf nodes that appear
in alist, a list ((old new) ...), will be replaced
by the corresponding new value.
(sublis '((rose peach) (smell taste))
'(a rose by any other name would smell as sweet))
= (a peach by any other name would taste as sweet)
- (filter fn lst )
filter applies fn to each element of lst,
returning a list of elements for which fn returns something
other than false or nil.
(filter (fn [x] (> x 3)) '(2 4 6 3 5)) = (4 6 5)
- (mapcat fn lst )
mapcat applies fn to each element of lst,
returning the concatenation of the results of fn. This means that
fn can return no result by returning nil or '(),
one result by returning (list result ), or
a list of multiple results. mapcat can be used with reduce
to map inputs to intermediate values, then reduce the intermediate values,
as in MapReduce.
(mapcat (fn [x] (if (number? x) (list x))) '(a 1 and a 2)) = (1 2)
(mapcat (fn [x] (if (symbol? x) (list x))) '(a 1 and a 2)) = (a and a)
(mapcat (fn [x] (if (= x 'z) (list 1))) '(z m u l e z r u l e z)) = (1 1 1)
(reduce +
(mapcat (fn [x] (if (= x 'z) (list 1))) '(z m u l e z r u l e z)))
= (reduce + '(1 1 1))
= 3
- (sort fn lst )
sort makes a new list in which the elements of lst
are sorted according to the predicate fn.
(sort > '(3 1 2 4 9)) = (9 4 3 2 1)
- (str args ... )
str makes a string of all of its args.
(let [var 3]
(str "var = " var) )
= "var = 3"
- (println args ... )
println prints all of its args.
(let [var 3]
(println "var = " var) )
var = 3
nil
In this case, println printed the value and then returned nil as
its value. Note that println has side-effects, so it should
be used within do or doseq.