[racket] Problem with macro
1. Without trying it, I'm pretty sure this particular syntax
transformation can be done in "syntax-rules", but I'm not certain it can
be done using only the power of "..." in "syntax-rules", without a
helper macro. Your life might be easier if you do this particular
transformation in "syntax-case" rather than "syntax-rules".
2. If you use "syntax-rules" instead of "syntax-case", three tips: (1)
break it up into mutiple macros, so you can have secret recursive helper
macros that have arguments for lists of input that you haven't processed
and arguments for lists of output from that processing, such as for
assembling lists of "letrec" or "case" clauses; (2) instead of
"process-state", you can have your helper macros assemble some of the
ultimate code *bottom-up*, so that, for example, things like the
"letrec" clauses (or "case" clauses, or parts of "case" clauses) get
assembled first, and only after all the clauses are assembled do the
"letrec" and other unchanging stuff around them get assembled; and (3)
it's good to expand to "case"/"if"/"and"/"or" for control flow, but
avoid expanding to "cond", because it's syntactic-sugary, and you'd have
to worry about "else" and "=>" appearing in your macro input.
3. You've picked a somewhat tricky macro for "syntax-rules" -- harder
than most "syntax-rules" macros you'll usually want to implement. But
once you can implement this macro, I think you'll then have the tools to
implement most any other "syntax-rules" macro you want to in the
future. If you get stuck on this one, try simpler ones that isolate a
single tricky part. For example, contrive a programming exercise of a
macro that's a thin veneer around "case", and implement your macro using
a recursive helper macro rather than "...", to assemble each "case"
clause, one clause per recursion step. (Or just use "syntax-case", and
be done with it.)
4. Before you spend too much time writing a macro for that particular
transformation, you might want to experiment some more with that example
you gave of code you're trying to transform to. See whether your state
transitions can simply can use tail calls to your "letrec" bindings for
the state closures, so that you need neither the "curr-state" variable
not the "ok" and "endstate" values. That would be more
Racket-idiomatic, the compiler might be able to optimize the code
better, and it might make your macro easier to implement.
(Pardon the writing in enumerations, but someone erroneously put caf
coffee in the decaf coffee carafe.)
--
http://www.neilvandyke.org/