Writing language converter in ANTLR

前端 未结 2 877
情话喂你
情话喂你 2021-01-14 18:10

I\'m writing a converter between some dialects of the same programming language. I\'ve found a grammar on the net - it\'s complex and handles all the cases. Now I\'m trying

相关标签:
2条回答
  • 2021-01-14 18:35

    Once you have an AST, you'll need to write a tree walker that emits your program as the transformed source. You might even have an intermediate tree walker doing tree transformations depending upon the complexity of your changes.

    That said, going through an AST step, may not be the best approach.

    You might want to take a look at "Language Design Patterns" by Terrence Parr (Pragmatic Programmers). Chapter 11 addresses your type of program.

    He mentions a tool, ANTLRMorph, that might be better suited for your problem.

    0 讨论(0)
  • 2021-01-14 18:38

    The easiest way is to create a rewriter. Set grammar to rewrite, use templates and create a template in-place. Then use TokenRewriteStream and it's ToString() method.

    grammar Test;
    
    options {
        language = CSharp2;
        output = template;
        rewrite = true;
    }
    
    program
        : statement_list
        ;
    
    //...
    
    statement
        :   expression_statement
        // ...
        ;
    
    expression_statement
        : function_call
        // ...
        ;
    
    function_call
        : ID '('                    { /* build the object, assign name */
                                      Function function = new Function();
                                      //...
                                    }
          (
          arg1 = expression         { /* add first parameter */ }
          ( ',' arg2 = expression   { /* add the rest of parameters */ }
          )*
          )?
          ')' -> { new StringTemplate(Tools.Convert(function)) }
        ;
    

    And the driver:

        string input = "....";
    
        var stream = new ANTLRStringStream(input);
        var lexer = new TestLexer(stream);
    
        // need to use TokenRewriteStream
        var tokenStream = new TokenRewriteStream(lexer);
        var parser = new TestParser(tokenStream);
    
        parser.program();
    
        // original text
        Console.WriteLine(tokenStream.ToOriginalString());
        // rewritten text
        Console.WriteLine(tokenStream.ToString());
    
    0 讨论(0)
提交回复
热议问题