Final Exam Review Examples

Pass By Name

Pass by name is an unusual parameter-passing mechanism originally used in Algol. Consider this function:

int twice(int x) {    // C++-like pseudocode
    x = 2 * x;
}

Suppose we call it like this using the variable vec[i]:

twice(vec[i]);

Then, if pass by name is used to pass vec[i], it’s as if we had written this textually replaced x with vec[i]:

vec[i] = 2 * vec[i];

Notice that this changes the value of vec[i], so it behaves a little bit like pass by reference.

If the actual parameter in pass-by-name is the same as the name of a local variable in the function it is being passed to, then it must be renamed to avoid a conflict. An example of pass-by-name where this sort of substitution is not done is in the C pre-processor, which does purely textual substitutions with no concern for the names of other variables in the same scope.

Sometimes, pass-by-name avoids the need to evaluate expressions, e.g.:

void f(float x, bool flag) {
    if (flag) {
        x = 2 * x;
    }
}

Using pass-by-name, it’s possible that x is not evaluated, e.g.:

f(vec[i], false)

// ... same as ...

if (false) {
    vec[i] = 2 * vec[i];
}

Evaluation of Lisp Expressions

Error messages have been simplified in the following transcript:

=> (a)
Error: Unable to resolve symbol: a in this context

=> (b)
Unable to resolve symbol: b in this context

=> (quote a)
a

=> (quote b)
b

=> (quote quote)
quote

=> (symbol? a)
Unable to resolve symbol: a in this context

=> (symbol? b)
Unable to resolve symbol: b in this context

=> (symbol? (quote a))
true

=> (symbol? (quote b))
true

=> (symbol? 'a)
true

=> (symbol? 'b)
true

=> (symbol? quote)   ;; quote is a special form
Unable to resolve symbol: quote in this context

=> (symbol? (quote quote))
true

=> (symbol? symbol?)
false

=> (symbol? (quote symbol?))
true

=> (symbol? 'symbol?)
true

=> (list? (1 2 3))
java.lang.Long cannot be cast to clojure.lang.IFn

=> (list? (quote (1 2 3)))
true

=> (quote (1 2 3))
(1 2 3)

=> (list? '(1 2 3))
true

=> '(1 2 3)
(1 2 3)

=> (quote (quote a))
(quote a)

=> (quote 'a)
(quote a)

=> ''a
(quote a)

=> (quote (quote quote))
(quote quote)

=> (quote 'quote)
(quote quote)

=> ''quote
(quote quote)

=> (list? quote)
Unable to resolve symbol: quote in this context

=> (list? 'quote)
false

=> (list? ''quote)
true

=> (list? '''quote)
true

=> '''quote
(quote (quote quote))

=> (first a)
Unable to resolve symbol: a in this context

=> (first (quote a))
Don't know how to create ISeq from: clojure.lang.Symbol

=> (first 'a)
Don't know how to create ISeq from: clojure.lang.Symbol

=> (first (quote (quote a)))
quote

=> (first (quote 'a))
quote

=> (first ''a)
quote

=> (rest (quote (quote a)))
(a)

=> (rest (quote 'a))
(a)

=> (rest ''a)
(a)

=> (first (rest ''a))
a

=> (rest (rest ''a))
()

=> (cons a (b c))
Unable to resolve symbol: a in this context

=> (cons 'a (b c))
Unable to resolve symbol: b in this context

=> (cons 'a '(b c))
(a b c)

=> (first (quote (quote a)))
quote

=> (first (quote 'a))
quote

=> (first ''a)
quote

=> (rest (quote (quote (quote a))))
((quote a))

=> (rest (quote (quote 'a)))
((quote a))

=> (rest (quote ''a))
((quote a))

=> (rest '''a)
((quote a))

=> (cons 'quote '((quote a)))
(quote (quote a))

=> (cons (first ''cat) (rest '''cat))
(quote (quote cat))

A Famous Lisp Quine

In programming, a Quine is a program that prints (or evaluates to) itself. Here is a Clojure Quine:

(

         (fn [x] (list x (list (quote quote) x)))

  (quote (fn [x] (list x (list (quote quote) x)))
  )

)

We’ve formatted it in a way to help show its structure. Lets try to understand what’s going on here.

First, note the expression has the form (f a), where f is a function and a is the argument passed into the function. So we can simplify it by using these two definitions:

(def f
    (fn [x] (list x (list (quote quote) x)))
)

(def a
    (quote (fn [x] (list x (list (quote quote) x))))
)

f is a function, so when you evaluate it you get this:

user=> f
#<user$f user$f@a2268a>

user=> (f 1)
(1 (quote 1))

user=> (f 2)
(2 (quote 2))

user=> (f 'a)
(a (quote a))

user=> (f 'b)
(b (quote b))

This makes it clear what (f e) does: it returns a 2-element list whose first element is e, and whose second element is (quote e).

We said the original Quine has the form (f a). That’s true, but we can be more specific. It also has the form (f (quote f)), i.e. it’s a list whose first element is f and whose second element is (quote f).

That’s exactly the form of list that a call to f returns. Thus:

=> (f (quote f))
(f (quote f))

This is a Quine: an expression that returns itself.

The original Quine is now easily created by replacing f (in => (f (quote f))) with it’s definition:

user=> ((fn [x] (list x (list (quote quote) x)))
(quote (fn [x] (list x (list (quote quote) x)))))

((fn [x] (list x (list (quote quote) x)))
(quote (fn [x] (list x (list (quote quote) x)))))