Allow letrec binding without init expression

For example, (letrec (... (x) ...) ...) is now allowed.

* lisp/subr.el (letrec): Allow omitted init expression.
* test/lisp/subr-tests.el (subr--tests-letrec): Add test case.
This commit is contained in:
Mattias Engdegård 2024-05-04 14:09:23 +02:00
parent 1e4cb12a81
commit fd859fbea2
2 changed files with 11 additions and 2 deletions

View file

@ -2281,7 +2281,9 @@ all symbols are bound before any of the VALUEFORMs are evalled."
(let ((nbody (if (null binders)
(macroexp-progn body)
`(let ,(mapcar #'car binders)
,@(mapcar (lambda (binder) `(setq ,@binder)) binders)
,@(mapcan (lambda (binder)
(and (cdr binder) (list `(setq ,@binder))))
binders)
,@body))))
(cond
;; All bindings are recursive.

View file

@ -744,7 +744,14 @@ See https://debbugs.gnu.org/cgi/bugreport.cgi?bug=19350."
(+ subr-tests-var1 subr-tests-var2)))
'(let* ((subr-tests-var1 1)
(subr-tests-var2 subr-tests-var1))
(+ subr-tests-var1 subr-tests-var2)))))
(+ subr-tests-var1 subr-tests-var2))))
;; Check that the init expression can be omitted, as in `let'/`let*'.
(should (equal (letrec ((a (lambda () (funcall c)))
(b)
(c (lambda () b)))
(setq b 'ok)
(funcall a))
'ok)))
(defvar subr-tests--hook nil)