ANTLR が初めてなので、文字列テンプレートがどのように機能するかを理解しようとしています。非常に単純な入力ファイルに基づいて Java コードを生成したいと考えています。柔軟なコンセプトのため、(文字列) テンプレートを使用したいと思います。Java では、通常、メンバー宣言を生成し、別の場所で初期化し、さらに別の場所で使用する必要があります。識別子名は一致する必要があるため、繰り返されます。これは、あちこちでテンプレートのインスタンス化がほとんど必要ないことを意味します。確かにそれは可能ですが、どうすればよいかわかりません。重要な「手がかり」が欠けているのではないでしょうか?
概念を調査するためのテスト プログラムを作成しました。単純な入力ファイルを取ります:
red = #FF0000
green = #00FF00
blue = #0000FF
次のような出力が生成されるはずです。
class MyColors {
// Class members
public java.awt.Color red;
public java.awt.Color green;
public java.awt.Color blue;
// Constructor
/* Question: How to access the right initializer value here?!? The values are not accessible at this level of the grammar*/
public MyColors() {
red = java.awt.Color.getColor("#FF0000");
green = java.awt.Color.getColor("#00FF00");
blue = java.awt.Color.getColor("#0000FF");
}
};
...コンストラクター内の変数と初期化子の名前は、入力に従って入力されます。
私が定義した文法は次のとおりです。
grammar Test;
options {
output=template;
}
colors: (a+=def)+ -> colorClassDef(name={$a});
def: ident '=' name -> colorDef(id={$ident.text}, name={$name.text});
ident: ID;
name: ID;
ID: ('a'..'z'|'A'..'Z'|'#'|'0'..'9')+;
WS: (' '|'\t'|'\r'|'\n')+ { skip(); };
テンプレートの定義は次のとおりです。
group Test;
colorClassDef(name, id) ::= <<
class MyColors {
// Class members
<name:{ v | public java.awt.Color <v>;
}>
// Constructor
/* Question: How to access the initializer value here?!? */
public MyColors() {
<name:{ v | <v> = java.awt.Color.getColor("<id>");
}>
}
};
>>
/* How to return both id and name here seperately, as ID should go into the declaration and name should to into the init? */
colorDef(id, name) ::= <<
<id>
>>
<id> と <name> をルール 'def' から取り出して、生成されたコードの正しい部分に含める方法を誰か提案できますか?
Returning multiple values in ANTLR ruleやantlr2 return multiple valuesなど、複数の戻り値に関する複数の質問を見つけましたが、文字列テンプレートは含まれていません。私は「本」を購入し、Java バイトコード ジェネレーターを調べてみましたが、そこに答えが見つかりませんでした。すべての例は、1 ビットの入力に対して 1 ビットの出力を生成するように見えます。(後悔はありませんが、この本は寝る前に読むのに最適です;-)
誰かが私が見逃している手がかりを指摘できますか? この問題を解決する最も適切な方法は何ですか? いくつかのサンプルコードとドキュメントへのポインタをいただければ幸いです。
ありがとう、
マールテン