2

関数とハッシュという、プログラミングにとって非常に重要であることに気付いた 2 つのことについて、非常に短い構文で DSL をプログラムしたいと思います。これは私のデザインです:

ハッシュを作成します:

(a:1 b:2 c:3)
Same as JavaScript's: {a:1,b:2,c:3}

キーを省略して、順序付きハッシュを作成します。

(x y 5) 
Same as JavaScript's: {0:'x', 1:'y', 2:5}

無名関数を作成します。

(a?)
Same as JavaScript's: (function(x){ return x.a; })
Example application:
    ((test a? b?) (a:1 b:2 c:3))
    >> Outputs (test 1 2)

ネストされた関数:

(a? a?') 
Same as JavaScript's: (function(obj1){ return function(obj2) { return [obj1.a,obj2.a]; }; })
Example double-application:
    (((a? a?') (a:1)) (a:2))
    Is reduced to: ((1 a?) (a:2))
    Then outputs: (1 2)

そのような DSL の実装に適した言語は何ですか?

4

1 に答える 1

5

ある種のSchemeのように、強力なマクロシステムを備えた言語が必要なようです。マクロを使用すると、まさにこの種の構文拡張が可能になり、元の言語のコードの断片を、提案する新しいフォームに埋め込むことができます ( などと言うことができるようになりたいと思います(a:1+1 b:2*2))。さらに、マクロ システムは、外部プリプロセッサのように、ビルド プロセスを複雑にしたり、エラー メッセージの場所を破壊したりしません。

しかし、悪いニュースがあります。私が知っている (非難解な) 言語で、指定した正確な構文を提供するのに十分な余地がある構文が存在しないということです。

私が思いついた構文は次のとおりです。

ハッシュ:

(: a 1 b 2 c 3)
; or, more clearly
(: (a 1) (b 2) (c 3))

インデックス キー付きハッシュ:

(:lst 'x 'y 5)

(ハッシュの RHS でベアワードを許可すると、変数を参照するのに苦労することになるので、それは望ましくないと思いました)

匿名の属性アクセス関数:

(anon. a)

前者と同様ですが、複数の引数をカリー化してリストを返します。

(anon. a a)

幸いなことに、この構文を Scheme に追加するために、レクサーやパーサーを作成したり、ビルド システムをいじったりする必要はありません。ほんの数行のコードであり、構文のインポートは関数のインポートと同じです。

最初のマクロ (名前:は ) は非常に簡単に記述できます。

(define-syntax-rule (: (k v) ...)
  (make-hash `((k ,v) ...)))

2 つ目 ( という名前:lst) は、インデックスを生成する必要があるため、より困難です。おそらく 10 行以下のコードになると思いますが、書くのが面倒です...

3 番目のマクロ ( anon.) は少し複雑ですが、ちょっと面白いので、以下に示します。

(define-syntax anon.
    (syntax-rules ()
      ((anon. attr attrs ...) 
       (lambda (x) (cons (hash-ref x 'attr) (anon. attrs ...) )))
      ((anon.)
        empty)))

(一貫性を保つために、常にリストを返す必要があると想定していることに注意してくださいanon.。そうしないとsyntax-rules、特別な場合に余分な句を追加する必要があります。)それanon.が本当に便利なマクロになるかどうかはわかりません。 、しかしそれはあなたとあなたのコードベースの間です。

マクロでハックしたい場合は、私のお気に入りの Scheme フレーバーであるRacketを試してみることをお勧めします。特にマクロ指向の世界観を持っています ( Racket が「PLT スキーム」と呼ばれていた頃に書かれたこのブログ投稿を参照してください)。

于 2012-09-05T04:47:19.393 に答える