Question

(car ''abracadabra) is equivalent to (car (quote (quote abracadabra)), and it evaluates to (car (quote abracadabra)) --> quote

On the othe hand (car (quote (a b))) evaluates to a, which to me makes sense intuitively.

So my question is, why does Scheme not evaluate the second quote in (car (quote (quote abracadabra)) (i.e. evaluate (car (quote abracadabra)) to (car abracadabra)), but does evaluade the quote in (car (quote (a b))) (i.e. why isn't the answer quote)?

Was it helpful?

Solution

In this expression:

(car (quote (quote abracadabra)))
=> 'quote

The inner quote doesn't get evaluated, it's just a symbol, with no particular meaning. You might as well change it for anything else, with the same results:

(car (quote (foobar abracadabra)))
=> 'foobar

Inside a quoted expression, other expressions won't get evaluated. We could use quasiquoting to force evaluation, now this will attempt to evaluate the inner quote, resulting in a different error for each case:

(car (quasiquote (unquote (quote abracadabra))))  ; (car `,(quote abracadabra))
=> car: contract violation expected: pair? given: 'abracadabra

(car (quasiquote (unquote (foobar abracadabra)))) ; (car `,(foobar abracadabra))
=> foobar: unbound identifier in module in: foobar

OTHER TIPS

Scheme doesn't evaluate the inner quote because the inner quote is inside the outer quote and expressions inside a quote aren't evaluated. That is if you write (quote foo), then foo will never be evaluated - even if foo is another call to quote.

When scheme evaluates a combination it evaluates the operator. Then it will apply if it's a special form or macro. If not, it will evaluate each operands before applying.

(car (quote (quote abracadabra)))

Can be evaluated like this*

  • car evaluates to #<proc car>. since it's a procedure evaluate all operands in any order
  • (quote (quote abracadabra)) is a combination, thus
    • quote is evaluated => #<macro quote> and since its a macro/special form do macro-apply
    • apply-macro (#<macro quote> (quote abracadabra))) => (quote abracadabra)
  • apply-proc (#<proc car> (quote abracadabra)) => quote

*Actually Scheme can shadow any keyword so the context is very important. E.g.:

(let ((quote list) (abracadabra 'simsalabim))
  (car (quote (quote abracadabra)))) 
==> (simsalabim)
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top