3

私はRacketマクロに飛び込み始めたばかりで、簡潔な単純なマクロ定義マクロを作成しようとしています。次のような式を拡張したいと思います。

(macro id
    (param) replacement1
    (params ...) replacement2)

このようなものに:

(define-syntax id
    (syntax-rules ()
        ((id param) replacement1)
        ((id params ...) replacement2)))

したがって、元の式のcddrは式のペアに変換され(構文ルールの本文で使用するため)、idはこれらの各ペアの車に挿入されます。

構文規則によって提供されるパターンマッチングのみを使用すると、再帰的に考えるのに問題があります(式を通常のリストであるかのように操作したいと思っています)。どんなパターンを使うべきですか?または、どういうわけかそれを通常のリストとして操作し、展開で使用するために結果の引用を解除することはできますか?

どうもありがとう

編集-Taymonの回答によって通知された暫定的な解決策

ここでの私の好奇心の一部は、それらのペアの括弧を取り除くことでした。構文の場合を調べましたが、少し混乱したので、純粋にパターンマッチングサブ言語でそれを実行しようとしました。最終的に、Taymonのマクロを別のマクロと組み合わせて使用​​して、指定されたテンプレートを「ペアリング」しました(アキュムレータ関数のように機能します)。

(define-syntax-rule (macro-aux id ((param ...) expr) ...)
  (define-syntax id
    (syntax-rules ()
      ((id param ...) expr)
      ...)))

(define-syntax pairize
  (syntax-rules ()
   ((pairize id (pairs ...) p b) (macro-aux id pairs ... (p b)))
   ((pairize id (pairs ...) p b rest ...) (pairize id (pairs ... (p b)) rest ...))))

(define-syntax macro
  (syntax-rules ()
    ((macro id tpl-expr ...) (pairize id () tpl-expr ...))))
4

2 に答える 2

7

構文式を通常の Racket データとして操作するマクロ エキスパンダーを構築することができます。ただし、この場合、それは実際には必要ありません。

私がお勧めすることの 1 つは、パターンと置換の各ペアが括弧で囲まれるように、構文を少し変更することです。このような:

(macro id
  [(param) replacement1]
  [(params ...) replacement2])

これが完了したら、通常のパターン マッチング マクロを使用できます。これが私の見解です:

(define-syntax-rule (macro id [(param ...) replacement] ...)
  (define-syntax id
    (syntax-rules ()
      [(id param ...) replacement] ...)))
于 2012-03-25T14:24:15.780 に答える
2

Taymon は正しいですが、 fromを使用して、パターンと置換のペアを括弧で囲まに楕円で行うこともできます。~seqsyntax/parse

(require syntax/parse/define)
(define-simple-macro (macro id (~seq (param ...) replacement) ...)
  (define-syntax id
    (syntax-rules ()
      [(id param ...) replacement] ...)))

あなたが最初に望んでいたように使用することができます:

(macro id
  (param) replacement1
  (params ...) replacement2)
于 2015-11-05T03:30:11.087 に答える