recursion - In Racket can I recursively process a syntax object like I would an s-expression? -


let's i'm using s-expressions ir language i'm writing. might have ast looks like

'(add (times (3 : int)              (add (4 : int)                   (5 : int)))       (1 : int)) 

which can process recursively without trouble. example, erase type annotations do

(define (erase-types term)   (match term     [`(,val : ,type)      val]     [`(,binop ,arg1 ,arg2)      `(,binop ,(erase-types arg1) ,(erase-types arg2))])) 

now suppose wanted same thing, instead @ compile time syntax object containing same datum ast @ top. tried use kind of pattern-based macro, seems can't use (define-syntax erase-types-or-whatever ...) in recursive way.

i tried putting normal match function in separate module (require (for-syntax ...)) , doing 1 big syntax->datum @ beginning, or doing like

(define (erase-types-or-whatever stx)   (match (syntax-e stx)     [...])) 

but have syntax->datum everywhere , have restructure again datum->syntax , don't know how use (do put #f first argument?) , feels absolute wrong way it.

what's correct way kind of syntax tree processing? docs aren't super enlightening either when comes macros , syntax.

#lang racket (require syntax/parse)  (define-syntax : (λ (stx) (raise-syntax-error ': "used out of context" stx)))  (define (erase-types term)   (syntax-parse term     #:literals (:)     [(val : type)      #'val]     [(binop arg1 arg2) (with-syntax ([arg1 (erase-types #'arg1)]                                      [arg2 (erase-types #'arg2)])                          #'(binop arg1 arg2))]))  (erase-types #'(add (times (3 : int)                            (add (4 : int)                                 (5 : int)))                     (1 : int))) 

Comments