need help with with-open-file() style macro

Discussion of Common Lisp

need help with with-open-file() style macro

Postby sinnatagg » Sat Jul 21, 2012 10:29 am

Ayup, I'm trying to create a macro binding a symbol in the same manner as with-open-file():

Code: Select all
(defmacro with-experiment ((experiment file) &body body)
  `(let* ((,experiment (read-experiment-file ,file)))
     ,@body))


This works but I'm a bit worried that "file" is evaluated before "experiment", but is this even a valid concern? with-open-file() and this code doesn't handle a non-symbol argument in this position.

Anybody know of any pitfalls in this regard?

-a
sinnatagg
 
Posts: 28
Joined: Tue Apr 21, 2009 3:04 am

Re: need help with with-open-file() style macro

Postby pjstirling » Sat Jul 21, 2012 11:57 am

This only matters in cases where you don't specify the order of evaluation in your documentation and it violates the principle of least surprise.

You are using experiment purely as a name, don't worry about it :)
pjstirling
 
Posts: 78
Joined: Sun Nov 28, 2010 4:21 pm

Re: need help with with-open-file() style macro

Postby Konfusius » Sat Jul 21, 2012 1:54 pm

Backquote replaces ,experiment by the value of the variable experiment. The value itself (that is, the actual argument to the macro) isn't evaluated.

The code

Code: Select all
(with-experiment ((car ex) "file")
  ...)

will be replaced by

Code: Select all
(let* (((car ex) (read-experiment-file "file)))
  ..)

which causes an error from let* because (car ex) isn't a symbol. But (car ex) wont be evaluated.

Since it can be confusing if an error is issued by let* though there is no let* in the source code your macro will become more user friendly if you add a check-type:

Code: Select all
(defmacro with-experiment ((experiment file) &body body)
  (check-type experiment symbol)
  `(let* ((,experiment (read-experiment-file ,file)))
     ,@body))
Konfusius
 
Posts: 62
Joined: Fri Jun 10, 2011 6:38 am


Return to Common Lisp

Who is online

Users browsing this forum: Google [Bot], Yahoo [Bot] and 2 guests

cron