Sign Up

Sign Up to our social questions and Answers Engine to ask questions, answer people’s questions, and connect with other people.

Have an account? Sign In

Have an account? Sign In Now

Sign In

Login to our social questions & Answers Engine to ask questions answer people’s questions & connect with other people.

Sign Up Here

Forgot Password?

Don't have account, Sign Up Here

Forgot Password

Lost your password? Please enter your email address. You will receive a link and will create a new password via email.

Have an account? Sign In Now

You must login to ask a question.

Forgot Password?

Need An Account, Sign Up Here

Please briefly explain why you feel this question should be reported.

Please briefly explain why you feel this answer should be reported.

Please briefly explain why you feel this user should be reported.

Sign InSign Up

The Archive Base

The Archive Base Logo The Archive Base Logo

The Archive Base Navigation

  • Home
  • SEARCH
  • About Us
  • Blog
  • Contact Us
Search
Ask A Question

Mobile menu

Close
Ask a Question
  • Home
  • Add group
  • Groups page
  • Feed
  • User Profile
  • Communities
  • Questions
    • New Questions
    • Trending Questions
    • Must read Questions
    • Hot Questions
  • Polls
  • Tags
  • Badges
  • Buy Points
  • Users
  • Help
  • Buy Theme
  • SEARCH
Home/ Questions/Q 6058817
In Process

The Archive Base Latest Questions

Editorial Team
  • 0
Editorial Team
Asked: May 23, 20262026-05-23T08:38:29+00:00 2026-05-23T08:38:29+00:00

I am having trouble with Lisp’s backquote read macro. Whenever I try to write

  • 0

I am having trouble with Lisp’s backquote read macro. Whenever I try to write a macro that seems to require the use of embedded backquotes (e.g., ``(w ,x ,,y) from Paul Graham’s ANSI Common Lisp, page 399), I cannot figure out how to write my code in a way that compiles. Typically, my code receives a whole chain of errors preceded with “Comma not inside a backquote.” Can someone provide some guidelines for how I can write code that will evaluate properly?

As an example, I currently need a macro which takes a form that describes a rule in the form of '(function-name column-index value) and generates a predicate lambda body to determine whether the element indexed by column-index for a particular row satisfies the rule. If I called this macro with the rule '(< 1 2), I would want a lambda body that looks like the following to be generated:

(lambda (row)
  (< (svref row 1) 2))

The best stab I can make at this is as follows:

(defmacro row-satisfies-rule (rule)
  (let ((x (gensym)))
    `(let ((,x ,rule))
       (lambda (row)
         (`,(car ,x) (svref row `,(cadr ,x)) `,(caddr ,x))))))

Upon evaluation, SBCL spews the following error report:

; in: ROW-SATISFIES-RULE '(< 1 2)
;     ((CAR #:G1121) (SVREF ROW (CADR #:G1121)) (CADDR #:G1121))
; 
; caught ERROR:
;   illegal function call

;     (LAMBDA (ROW) ((CAR #:G1121) (SVREF ROW (CADR #:G1121)) (CADDR #:G1121)))
; ==>
;   #'(LAMBDA (ROW) ((CAR #:G1121) (SVREF ROW (CADR #:G1121)) (CADDR #:G1121)))
; 
; caught STYLE-WARNING:
;   The variable ROW is defined but never used.

;     (LET ((#:G1121 '(< 1 2)))
;       (LAMBDA (ROW) ((CAR #:G1121) (SVREF ROW (CADR #:G1121)) (CADDR #:G1121))))
; 
; caught STYLE-WARNING:
;   The variable #:G1121 is defined but never used.
; 
; compilation unit finished
;   caught 1 ERROR condition
;   caught 2 STYLE-WARNING conditions
#<FUNCTION (LAMBDA (ROW)) {2497F245}>

How can I write macros to generate the code I need, and in particular, how do I implement row-satisfies-rule?


Using the ideas from Ivijay and discipulus, I have modified the macro so that it compiles and works, even allowing forms to be passed as the arguments. It runs a bit differently from my originally planned macro since I determined that including row as an argument made for smoother code. However, it is ugly as sin. Does anyone know how to clean it up so it performs the same without the call to eval?

(defmacro row-satisfies-rule-p (row rule)
  (let ((x (gensym))
        (y (gensym)))
    `(let ((,x ,row)
           (,y ,rule))
       (destructuring-bind (a b c) ,y
         (eval `(,a (svref ,,x ,b) ,c))))))

Also, an explanation of clean, Lispy ways to get macros to generate code to properly evaluate the arguments at runtime would be greatly appreciated.

  • 1 1 Answer
  • 0 Views
  • 0 Followers
  • 0
Share
  • Facebook
  • Report

Leave an answer
Cancel reply

You must login to add an answer.

Forgot Password?

Need An Account, Sign Up Here

1 Answer

  • Voted
  • Oldest
  • Recent
  • Random
  1. Editorial Team
    Editorial Team
    2026-05-23T08:38:29+00:00Added an answer on May 23, 2026 at 8:38 am

    First of all, Lisp macros have “destructuring” argument lists. This is a nice feature that means instead of having an argument list (rule) and then taking it apart with (car rule) (cadr rule) (caddr rule), you can simply make the argument list ((function-name column-index value)). That way the macro expects a list of three elements as an argument, and each element of the list is then bound to the corresponding symbol in the arguemnt list. You can use this or not, but it’s usually more convenient.

    Next, `, doesn’t actually do anything, because the backquote tells Lisp not to evaluate the following expression and the comma tells it to evaluate it after all. I think you meant just ,(car x), which evaluates (car x). This isn’t a problem anyway if you use destructuring arguments.

    And since you’re not introducing any new variables in the macro expansion, I don’t think (gensym) is necessary in this case.

    So we can rewrite the macro like this:

    (defmacro row-satisfies-rule ((function-name column-index value))
      `(lambda (row)
         (,function-name (svref row ,column-index) ,value)))
    

    Which expands just how you wanted:

    (macroexpand-1 '(row-satisfies-rule (< 1 2)))
    => (LAMBDA (ROW) (< (SVREF ROW 1) 2))
    

    Hope this helps!


    If you need the argument to be evaluated to get the rule set, then here’s a nice way to do it:

    (defmacro row-satisfies-rule (rule)
      (destructuring-bind (function-name column-index value) (eval rule)
        `(lambda (row)
           (,function-name (svref row ,column-index) ,value))))
    

    Here’s an example:

    (let ((rules '((< 1 2) (> 3 4))))
      (macroexpand-1 '(row-satisfies-rule (car rules))))
    => (LAMBDA (ROW) (< (SVREF ROW 1) 2))
    

    just like before.


    If you want to include row in the macro and have it give you your answer straightaway instead of making a function to do that, try this:

    (defmacro row-satisfies-rule-p (row rule)
      (destructuring-bind (function-name column-index value) rule
        `(,function-name (svref ,row ,column-index) ,value)))
    

    Or if you need to evaluate the rule argument (e.g. passing '(< 1 2) or (car rules) instead of (< 1 2)) then just use (destructuring-bind (function-name column-index value) (eval rule)


    Actually, a function seems more appropriate than a macro for what you’re trying to do. Simply

    (defun row-satisfies-rule-p (row rule)
      (destructuring-bind (function-name column-index value) rule
        (funcall function-name (svref row column-index) value)))
    

    works the same way as the macro and is much neater, without all the backquoting mess to worry about.

    In general, it’s bad Lisp style to use macros for things that can be accomplished by functions.

    • 0
    • Reply
    • Share
      Share
      • Share on Facebook
      • Share on Twitter
      • Share on LinkedIn
      • Share on WhatsApp
      • Report

Sidebar

Related Questions

Having trouble with proper regex for RewriteCond RewriteCond %{REQUEST_URI} !^/foo/ Works as expected, that
Having trouble getting this to work. What's strange is that I have 10 bookmarks
I'm just learning LISP and i am having trouble doing the following: ; return
Having trouble linking the Stomp.framework into an iPhone SDK application. http://code.google.com/p/stompframework/ I follow the
Having trouble with the following segment of code. I'm getting a parameter count mismatch.
Having Trouble with Entity Framework. I have been populating EntityReferences with an EntityKey inorder
Im having trouble using a .NET COM in vb6, It compiles ok and I
I having trouble in dividing the HTML frames. I have been using the following
I`m having trouble trying to optimize this query with OVER (PARTITION BY ...) because
im having trouble figuring out how to bind mouseout() to my entire nav bar

Explore

  • Home
  • Add group
  • Groups page
  • Communities
  • Questions
    • New Questions
    • Trending Questions
    • Must read Questions
    • Hot Questions
  • Polls
  • Tags
  • Badges
  • Users
  • Help
  • SEARCH

Footer

© 2021 The Archive Base. All Rights Reserved
With Love by The Archive Base

Insert/edit link

Enter the destination URL

Or link to existing content

    No search term specified. Showing recent items. Search or use up and down arrow keys to select an item.