Chapter 10 练习 (Exercises)

  1. 如果 xayb 以及 z(c d) ,写出反引用表达式仅包含产生下列结果之一的变量:
  1. (a) ((C D) A Z)
  2. (b) (X B C D)
  3. (c) ((C D A) Z)
  1. 使用 cond 来定义 if
  2. 定义一个宏,接受一个数字 n ,伴随着一个或多个表达式,并返回第 n 个表达式的值:
  1. > (let ((n 2))
  2. (nth-expr n (/ 1 0) (+ 1 2) (/ 1 0)))
  3. 3
  1. 定义 ntimes (167 页,译注: 10.5 节)使其展开成一个 (区域)递归函数,而不是一个 do 表达式。
  2. 定义一个宏 n-of ,接受一个数字 n 与一个表达式,返回一个 n 个渐进值:
  1. > (let ((i 0) (n 4))
  2. (n-of n (incf i)))
  3. (1 2 3 4)
  1. 定义一个宏,接受一变量列表以及一个代码主体,并确保变量在代码主体被求值后恢复 (revert)到原本的数值。
  2. 下面这个 push 的定义哪里错误?
  1. (defmacro push (obj lst)
  2. `(setf ,lst (cons ,obj ,lst)))
  3. 举出一个不会与实际 push 做一样事情的函数调用例子。
  1. 定义一个将其参数翻倍的宏:
  1. > (let ((x 1))
  2. (double x)
  3. x)
  4. 2

脚注

[1]要真的复制一个 Lisp 的话, eval 会需要接受第二个参数 (这里的 env) 来表示词法环境 (lexical enviroment)。这个模型的 eval 是不正确的,因为它在对参数求值前就取出函数,然而 Common Lisp 故意没有特别指出这两个操作的顺序。