(defun foo (x) (wrapper-macro (bar 42 x)))Where
wrapper-macro
simply prints ‘Normal exit’ or ‘Throw’ as control returns from bar
through foo
. (If bar
returns normally, all the return values are returned from foo
after wrapper-macro
prints. If bar
exits via a throw, then the throw continues after wrapper-macro
prints.)The challenge: Implement
wrapper-macro
.(If you wish, imagine that
wrapper-macro
simply expands to this:(defun foo (x) (wrapper-function (lambda () (bar 42 x))))and the challenge is to implement
wrapper-function
.)
(defun wrapper-function (thunk)
ReplyDelete(let ((return? nil))
(unwind-protect
(multiple-value-prog1
(funcall thunk)
(setf return? t))
(if return?
(print "Return")
(print "Non-local exit")))))
Btw, if possible, please allow the use of PRE tags in comments in order to display code fragments properly
I wish I could turn on PRE tags.
ReplyDeleteIf you untabify and replace the spaces with , you get this:
(defun wrapper-function (thunk)
(let ((return? nil))
(unwind-protect
(multiple-value-prog1
(funcall thunk)
(setf return? t))
(if return?
(print "Return")
(print "Non-local exit")))))
I might be wrong, but can't you just do it with call/cc and modifying bar function to use continuations?
ReplyDeleteohw0w said...
ReplyDeleteCan't you just do it with call/cc and modifying bar function to use continuations?
Yikes! I don't think you need to haul out the heavy machinery!