個人的な理由で設計している C/C++/C#/Java/D に似たプログラミング言語用のスキャナーを作成しようとしています。このタスクでは、Ragel を使用してスキャナーを生成しています。多くのオペレーターがアクションをトリガーするタイミングを正確に理解するのに苦労しています。おそらく、私の学者は理論よりも実践的な知識に焦点を当てていたためであり、この非決定論的/決定論的な有限オートマトン ビジネスの多くが私の頭の中にあります。ドキュメントが不足しているか、それについての私の理解が不足していると思います。私は後者を想定しています。
いずれにせよ、私は基本から上に向かって取り組んでいます。最初の繰り返しで、いくつかのキーワードと特殊文字を特定しました。今、すべてのキーワードが識別子としてスキャンされているという問題に遭遇しました。すべてのキーワードにスキャナー演算子を使用しています。これにより、文字列がandキーワードreturns
の両方としてスキャンされるという問題が解決されました。return
returns
識別子を正しくスキャンするにはどうすればよいですか? identifier
これを決定論的にするには、他のトークンのパターンと一致しない場合にのみ語彙素が になることを効果的に指定する必要があることを理解しています。私の知識不足をお許しください。
Ragel スクリプト:
%%{
Identifier = (alpha | '_') . (alnum | '_')*;
action IdentifierAction
{
std::cout << "identifier(\"";
std::cout.write(ts, te - ts);
std::cout << "\")";
}
}%%
%%{
main :=
|*
Interface => InterfaceAction;
Class => ClassAction;
Property => PropertyAction;
Function => FunctionAction;
TypeQualifier => TypeQualifierAction;
OpenParenthesis => OpenParenthesisAction;
CloseParenthesis => CloseParenthesisAction;
OpenBracket => OpenBracketAction;
CloseBracket => CloseBracketAction;
OpenBrace => OpenBraceAction;
CloseBrace => CloseBraceAction;
Semicolon => SemicolonAction;
Returns => ReturnsAction;
Return => ReturnAction;
Identifier => IdentifierAction;
space+;
*|;
}%%