ccl
ccl copied to clipboard
NFUNCTION with a constructed LAMBDA
On SBCL, the following works:
CL-USER> (let ((lambda-list '(a))
(body 'a))
(compile nil `(sb-int:named-lambda (my-fun-name) ,lambda-list ,body)))
#<FUNCTION (MY-FUN-NAME) {52EAE99B}>
NIL
NIL
Is there an equivalent way to do things on CCL without using eval
?
CL-USER> (let ((lambda-list '(a))
(body 'a))
(compile nil `(ccl:nfunction (my-fun-name) (lambda ,lambda-list ,body))))
; raises error about invalid lambda expression
; Evaluation aborted on #<CCL::COMPILE-TIME-PROGRAM-ERROR #x30200229194D>.
The best I can find is ccl::cheap-eval-function
, e.g. (ccl::cheap-eval-function 'foo '(lambda () 42) nil)
. I assume that someday cl:compile
could be extended to accept nfunction
forms.
Hmm, the difference seems minor, and compute-cost is not a concern for the purpose. So, either should work I guess. (EDIT: May be the difference adds up for larger function bodies?)
CL-USER> (let ((lambda-list '(a))
(body 'a))
(time (loop repeat 1000
do (ccl::cheap-eval-function '(my-fun-name)
`(lambda ,lambda-list ,body) nil))))
(LOOP REPEAT 1000 DO (CCL::CHEAP-EVAL-FUNCTION '(MY-FUN-NAME) (LIST* 'LAMBDA (LIST* LAMBDA-LIST (LIST BODY))) NIL))
took 268,474 microseconds (0.268474 seconds) to run.
3,313 microseconds (0.003313 seconds, 1.23%) of which was spent in GC.
During that period, and with 12 available CPU cores,
272,559 microseconds (0.272559 seconds) were spent in user mode
32 microseconds (0.000032 seconds) were spent in system mode
10,192,000 bytes of memory allocated.
NIL
CL-USER> (let ((lambda-list '(a))
(body 'a))
(time (loop repeat 1000
do (eval `(ccl:nfunction (my-fun-name)
(lambda ,lambda-list ,body))))))
(LOOP REPEAT 1000 DO (EVAL (LIST* 'NFUNCTION (LIST* '(MY-FUN-NAME) (LIST (LIST* 'LAMBDA (LIST* LAMBDA-LIST (LIST BODY))))))))
took 272,228 microseconds (0.272228 seconds) to run.
2,987 microseconds (0.002987 seconds, 1.10%) of which was spent in GC.
During that period, and with 12 available CPU cores,
276,055 microseconds (0.276055 seconds) were spent in user mode
0 microseconds (0.000000 seconds) were spent in system mode
10,240,096 bytes of memory allocated.
NIL