2

シンプルな Irony パーサーを作成しようとしています。文法はあるはずです

これらの 1 つまたは複数を認識できる

setlink("文字列");

1 つの keyword() 呼び出しは正常に認識されているようですが、2 つの連続した呼び出しは失敗します。エラーステータスが表示されます。メインで parseTree 変数を調べると、解析を停止する前に識別される最後のトークンが、「connect」トークンの最初の文字である文字「c」であることがわかります。ここで何が欠けているのか誰か教えてもらえますか?

code.txt の内容

 setlink("stuffs");
 connect("things");

LilGrammar.cs

 using System;
 using System.Collections.Generic;
 using System.Linq;
 using System.Security;
 using System.Text;
 using System.Threading.Tasks;
 using Irony.Parsing;

 namespace IronyTest
 {
 public class LilGrammar : Grammar
 {
   public LilGrammar()
   {

        //Define terminals

       var program = new NonTerminal("program");
       var command = new NonTerminal("command");
       var commandList = new NonTerminal("commandList");
       var keyword = new NonTerminal("keyword");
       var stringLiteral = new StringLiteral("string", "\"", StringOptions.None);

       var LPAREN = ToTerm("(");
       var RPAREN = ToTerm(")");
       var SEMICO = ToTerm(";");
       var NL = ToTerm("\n");         
       this.Root = program;

       program.Rule = command + Eof;

       keyword.Rule = ToTerm("setlink") | "connect";
       command.Rule = keyword + LPAREN + stringLiteral + RPAREN + SEMICO;  
       commandList.Rule = MakePlusRule(commandList,null , command);
       this.Root = program;

       MarkPunctuation(";");
   }
}
 }

Main.cs

 using System;
 using System.Collections.Generic;
 using System.Linq;
 using System.Text;
 using System.Threading.Tasks;
 using Irony.Parsing;
 using Irony;
 using System.IO;

 namespace IronyTest
 {
 private static void Main(string[] args)
    {
        Grammar grammar = new LilGrammar();
        var parser = new Parser(grammar);
        string path = @"c:\code\code.txt";


        // Open the file to read from. 
        string readText = File.ReadAllText(path);


        //Returns the root to a parase tree
        //var tree = parser.Parse(readText, path);
        ParseTree parseTree = parser.Parse(readText,path);
        ParseTreeNode root = parseTree.Root;
 }
4

1 に答える 1

4

修正は、プログラムを1つのコマンドだけでなく、コマンドのリストで構成することだと思います。

したがって、次の変更により、正しく解析されるように見えます。ToTerm("connect")の setlink のように見えるようにしたこと、 の定義を の定義の後keyword.Ruleに移動したこと、 ではなくを参照するように変更したことに注意してください。program.RulecommandList.Ruleprogram.RulecommandListcommand

keyword.Rule = ToTerm("setlink") | ToTerm("connect");
command.Rule = keyword + LPAREN + stringLiteral + RPAREN + SEMICO;
commandList.Rule = MakePlusRule(commandList, command);
program.Rule = commandList + Eof;
this.Root = program;
于 2015-05-06T22:18:41.740 に答える