[R6RS] Bawden quasiquote extension

dyb at cs.indiana.edu dyb at cs.indiana.edu
Thu Jun 22 16:34:08 EDT 2006


The syntax-case reference implementation implements the nested quasiquote
extensions and it does what you say (and I agree) the R5RS mandates.

  > (let ([q '((union x y) (list 'sqrt 9))])
      ``(foo ,, at q))
  `(foo (unquote (union x y) (list 'sqrt 9)))

The output would be invalid syntax, as you say, in R5RS and Common Lisp,
but not with Bawden's quasiquote extensions.  With the extensions, if the
output is in turn evaluated with x bound to '(a b c), y set to '(a c e),
and union set to the obvious procedure, we get:

  > (letrec ([x '(a b c)]
             [y '(a c e)]
             [union
              (lambda (s1 s2)
                (if (null? s1)
                    s2
                    (cons (car s1) (remq (car s1) s2))))])
      `(foo (unquote (union x y) (list 'sqrt 9))))
  (foo (a c e) (sqrt 9))

If we evaluate the output from the expander in Bawden's appendix with
the same binding for q:

  > (let ([q '((union x y) (list 'sqrt 9))])
      (append
        '(append)
        (append
          (list (append
                  '(quote)
                  (append (list (append '(foo) '())) '())))
          (append
            (list (append
                    '(append)
                    (append
                      (list (append '(list) (append q '())))
                      (append
                        (list (append '(quote) (append '(()) '())))
                        '()))))
            '()))))
  (append
    '(foo)
    (append (list (union x y) (list 'sqrt 9)) '()))

then evaluate this output with the same bindings for x, y, and union:

  > (letrec ([x '(a b c)]
             [y '(a c e)]
             [union
              (lambda (s1 s2)
                (if (null? s1)
                    s2
                    (cons (car s1) (remq (car s1) s2))))])
      (append
        '(foo)
        (append (list (union x y) (list 'sqrt 9)) '())))
  (foo (a c e) (sqrt 9))

we get the same final result.

While the intermediate form from Bawden's expander is incompatible with
R5RS, the intermediate form from the reference implementation is not.

So I don't think there's an inherent incompatibility.

BTW, the reference implementation generates reasonably tight code:

  > (sc-expand '``(foo ,, at q))
  (cons 'quasiquote (cons (cons 'foo (cons (cons 'unquote q) '())) '()))

  > (sc-expand '`(foo (unquote (union x y) (list 'sqrt 9))))
  (cons 'foo (cons (union x y) (cons (list 'sqrt '9) '())))

but not as good as the portable syntax-case expander from which the
reference implementation was derived, which generates:

  > (sc-expand '``(foo ,, at q))
  (list 'quasiquote (list 'foo (cons 'unquote q)))

I decided to try to simplify things a bit in the reference implementation. 
Maybe I should unsimplify it in the spirit providing a more efficient
reference implementation.

Kent



More information about the R6RS mailing list