(defun lrec (rec &optional base)
(labels ((self (lst)
(if (null lst)
(if (functionp base)
(funcall base)
base)
(funcall rec (car lst)
#'(lambda ()
(self (cdr lst)))))))
(lrec #'(lambda (x f) (1+ (funcall f))) 0)
(lrec #'(lambda (x f) (and (oddp x) (funcall f))) t)
看不懂,自己推导一下
大概样子:
(defun lrec1 (op lst base join)
(if (null lst)
base
(funcall join (funcall op (car lst))
(lrec1 op (cdr lst) base join))))
可以把 lst 抽出来:
(defun lrec2 (op base join)
(labels ((self (lst)
(if (null lst)
base
(funcall join (funcall op (car lst)) (funcall (lrec2 op base join) (cdr lst))))))
#'self))
------->
(defun lrec2 (op base join)
(labels ((self (lst)
(if (null lst)
base
(funcall join (funcall op (car lst)) (funcall self (cdr lst))))))
#'self))
op和join是宏的话,就不行了,所以把op和join放到一个函数里在传入:
函数的样子是这样的 (lambda (x) (join (op x) (self (cdr lst))))
(self (cdr lst))由调用者传给它
最后就是这样子的 (lambda (x f) (join (op x) (funcall f)))
(defun lrec4 (rec base)
(labels ((self (lst)
(if (null lst)
base
(funcall rec (car lst)
#'(lambda ()
(self rec (cdr lst)))))))
(收起)