Skip to content

Commit

Permalink
WIP Add letf
Browse files Browse the repository at this point in the history
  • Loading branch information
ruricolist committed Oct 16, 2023
1 parent bd549f1 commit 3aa32b6
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 2 deletions.
38 changes: 38 additions & 0 deletions letf.lisp
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
(in-package :serapeum)

(defun letf-bindings (bindings env)
(with-collectors (savers setters restorers)
(loop for (place expr) in bindings do
(multiple-value-bind (vars vals stores setter getter)
(get-setf-expansion place env)
(let ((saves (make-gensym-list (length stores))))
(mapc #'savers (mapcar #'list vars vals))
(savers
`(,@saves ,getter))
(setters
`(mvlet ((,@stores ,expr))
,setter))
(restorers
`(mvlet ((,@stores (values ,@saves)))
,setter)))))))

(defmacro letf* (bindings &body body)
(if (no bindings) `(locally ,@body)
`(letf ,(firstn 1 bindings)
(letf* ,(rest bindings)
,@body))))

(defmacro letf (bindings &body body &environment env)
(if (no bindings) `(locally ,@body)
(mvlet ((savers setters restorers (letf-bindings bindings env)))
`(mvlet* ,savers
(unwind-protect
(progn
,@setters
(locally ,@body))
,@restorers)))))

(comment
(letf (((car xs) 1)
((cdr ys) 2))
(list xs ys)))
5 changes: 4 additions & 1 deletion package.lisp
Original file line number Diff line number Diff line change
Expand Up @@ -523,7 +523,10 @@
;; Units.
#:si-prefix
#:human-size-formatter
#:format-human-size))
#:format-human-size
;; Left
#:letf
#:letf*))

(defpackage #:serapeum-user
(:use #:cl #:alexandria #:serapeum))
Expand Down
3 changes: 2 additions & 1 deletion serapeum.asd
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,8 @@
(:file "dispatch-case")
(:file "range" :depends-on ("dispatch-case"))
(:file "generalized-arrays" :depends-on ("range"))
(:file "units")))
(:file "units")
(:file "letf")))
(:module "contrib"
:components
((:file "hooks")))))
Expand Down

0 comments on commit 3aa32b6

Please sign in to comment.