----- Original Message ----- From: "marcomaggi" <[EMAIL PROTECTED]>
To: "ikarus-users" <[email protected]>
Sent: Sunday, November 09, 2008 3:56 PM
Subject: [ikarus-users] define-macro



Help a guy out!

Both because I need it and as an exercise in learning
SYNTAX-CASE I have tried for hours to write a Common
Lisp like DEFINE-MACRO.  I could not get around how to use/modify/
whatever:

(define lisp-transformer
 (lambda (p)
   (lambda (x)
     (syntax-case x ()
((keyword . rest)
(datum->syntax (syntax keyword)
(p (syntax->datum x))))))))

nor how to change the implementation in the PLT Scheme
module "defmacro.ss".

Finally, after a lot of headbanging, I have this:

;; this-file.sls --

(import (ikarus)
(srfi lightweight-testing))

(check-set-mode! 'report-failed)

(define-syntax define-macro
 (lambda (incoming)
   (syntax-case incoming ()
     ((_ (?name ?arg ...) ?form ...)
      (syntax
(define-macro ?name (lambda (?arg ...) ?form ...))))
     ((_ ?name ?func)
      (syntax
(define-syntax ?name
  (lambda (x)
    (syntax-case x ()
      ((kwd . rest)
       (datum->syntax #'kwd (apply ?func (cdr (syntax->datum
x))))))))))
     )))

(check
(let ()
  (define-macro (proof a b c)
    `(list ,a ,b ,c))
  (proof 'one 'two 'three))
=> '(one two three))

(check
(let ()
  (define-macro (proof a b c)
    `(,a ,(+ 1 b) ,c))
  (proof list 123 'three))
=> '(124 three))

(let ()
 (define-macro (false-if-exception expr)
   `(guard (exc (else #f))
    ,expr))

 (check
  (false-if-exception (list 1 2 3))
  => '(1 2 3))

 (check
  (false-if-exception (raise 'slap))
  => #f))

(check-report)

;;; end of file

which I do not fully understand but seems to work.
Is it actually correct?

TIA


Here is one Will Clinger (I think) posted a while back on comp.lang.scheme:

(define-syntax define-macro
  (lambda (x)
    (syntax-case x ()
      [(_ (name . params) body1 body2 ...)
       #'(define-macro name (lambda params body1 body2 ...))]
      [(_ name expander)
       #'(define-syntax name
           (lambda (y)
             (syntax-case y ()
               ((k . args)
                (let ((lst (syntax->datum #'args)))
                  (datum->syntax #'k (apply expander lst)))))))]
       )))

Definitely easier to understand  :)

Cheers

leppie

Reply via email to