2017-08-29 9 views
11

मैंने इंटेलिजे में एएनटीएलआर 4 plugin का उपयोग करके इस नमूना व्याकरण को बनाया है और जब मैं कुछ अमान्य सामग्री (इस मामले में एक खाली स्ट्रिंग) के लिए दृश्य प्रस्तुतिकरण उत्पन्न करने के लिए अपनी टूल श्रृंखला का उपयोग करता हूं, तो यह प्रतिनिधित्व मुझे जो कुछ भी है उससे अलग दिखता है एक ही इनपुट के लिए एक नमूना आगंतुक/श्रोता कार्यान्वयन का उपयोग कर वास्तविक पार्स पेड़ ट्रैवर्सल करते समय प्राप्त करने में सक्षम।पार्स ट्री विज़ुअलाइज़ेशन और मेरे विज़िटर/श्रोता ट्रैवर्सल के बीच इतना अंतर क्यों है?

यह व्याकरण है:

grammar TestParser; 

THIS   : 'this'; 

Identifier 
    : [a-zA-Z0-9]+ 
    ; 

WS : [ \t\r\n\u000C]+ -> skip; 

parseExpression: 
    expression EOF 
; 

expression 
    : expression bop='.' (Identifier | THIS) #DottedExpression 
    | primary         #PrimaryExpression 
    ; 

primary 
     : THIS        #This 
     | Identifier       #PrimaryIdentifier 
     ; 

कोई रिक्त स्ट्रिंग के लिए, मैं निम्नलिखित पेड़ मिलती है:

parse tree

इस पेड़ इंगित करता है कि पार्सर एक पार्स पेड़ कि शामिल है "DottedExpression बनाया "और" प्राथमिक: यह "(मानते हुए कि यह करने के लिए यह अपने स्वयं के आगंतुक/श्रोता कार्यान्वयन का उपयोग करता है)। फिर भी जब मैं निम्नलिखित कोड का उपयोग कर एक ही प्रयास:

package org.example.so; 

import org.antlr.v4.runtime.CharStreams; 
import org.antlr.v4.runtime.CommonTokenStream; 
import org.antlr.v4.runtime.tree.ParseTreeWalker; 

public class TestParser { 
    public static void main(String[] args) { 
     String input = ""; 
     TestParserLexer lexer = new TestParserLexer(CharStreams.fromString(input)); 
     CommonTokenStream tokenStream = new CommonTokenStream(lexer); 
     TestParserParser parser = new TestParserParser(tokenStream); 

     TestParserParser.ParseExpressionContext parseExpressionContext = parser.parseExpression(); 

     MyVisitor visitor = new MyVisitor(); 
     visitor.visit(parseExpressionContext); 

     System.out.println("----------------"); 

     ParseTreeWalker walker = new ParseTreeWalker(); 
     walker.walk(new MyListener(), parseExpressionContext); 

     System.out.println("----------------"); 
    } 

    private static class MyVisitor extends TestParserBaseVisitor { 

     @Override 
     public Object visitParseExpression(TestParserParser.ParseExpressionContext ctx) { 
      System.out.println(TestParserParser.ruleNames[ctx.getRuleIndex()]); 
      return super.visitParseExpression(ctx); 
     } 

     @Override 
     public Object visitDottedExpression(TestParserParser.DottedExpressionContext ctx) { 
      System.out.println(TestParserParser.ruleNames[ctx.getRuleIndex()] + ":DottedExpression"); 
      return super.visitDottedExpression(ctx); 
     } 

     @Override 
     public Object visitPrimaryExpression(TestParserParser.PrimaryExpressionContext ctx) { 
      System.out.println(TestParserParser.ruleNames[ctx.getRuleIndex()] + ":PrimaryExpression"); 
      return super.visitPrimaryExpression(ctx); 
     } 

     @Override 
     public Object visitThis(TestParserParser.ThisContext ctx) { 
      System.out.println(TestParserParser.ruleNames[ctx.getRuleIndex()]); 
      return super.visitThis(ctx); 
     } 

     @Override 
     public Object visitPrimaryIdentifier(TestParserParser.PrimaryIdentifierContext ctx) { 
      System.out.println(TestParserParser.ruleNames[ctx.getRuleIndex()]); 
      return super.visitPrimaryIdentifier(ctx); 
     } 
    } 

    private static class MyListener extends TestParserBaseListener { 

     @Override 
     public void enterParseExpression(TestParserParser.ParseExpressionContext ctx) { 
      System.out.println(TestParserParser.ruleNames[ctx.getRuleIndex()]); 
     } 

     @Override 
     public void enterDottedExpression(TestParserParser.DottedExpressionContext ctx) { 
      System.out.println(TestParserParser.ruleNames[ctx.getRuleIndex()] + ":DottedExpression"); 
     } 

     @Override 
     public void enterPrimaryExpression(TestParserParser.PrimaryExpressionContext ctx) { 
      System.out.println(TestParserParser.ruleNames[ctx.getRuleIndex()] + ":PrimaryExpression"); 
     } 

     @Override 
     public void enterThis(TestParserParser.ThisContext ctx) { 
      System.out.println(TestParserParser.ruleNames[ctx.getRuleIndex()]); 
     } 

     @Override 
     public void enterPrimaryIdentifier(TestParserParser.PrimaryIdentifierContext ctx) { 
      System.out.println(TestParserParser.ruleNames[ctx.getRuleIndex()]); 
     } 
    } 
} 

मैं निम्नलिखित उत्पादन प्राप्त करें:

line 1:0 mismatched input '<EOF>' expecting {'this', Identifier} 
parseExpression 
expression:PrimaryExpression 
---------------- 
parseExpression 
expression:PrimaryExpression 
---------------- 

तो, न केवल पेड़ गहराई से मेल नहीं खाते, उत्पादन भी इंगित करता है एक अलग नियम मिलान किया गया था ("DottedExpression" के बजाय "PrimaryExpression")।

मुझे जो दिखाया गया है और मैं क्या दिखाने का प्रयास करता हूं, उसके बीच इतना अंतर क्यों है? प्लगइन द्वारा दिखाए गए अनुसार मैं एक ही पेड़ का प्रतिनिधित्व कैसे करूं?

एएनटीएलआर संस्करण 4.7 का उपयोग करना। प्लगइन संस्करण 1.8.4 है।

+0

एएनटीएलआर स्रोत पर एक त्वरित नज़र डालें। मेरा अनुमान है कि जब आप पार्सर चलाते हैं तो आप पार्सल के साथ ग्राफिकल पार्स पेड़ को एक अलग भविष्यवाणी मोड में बनाया जा रहा है। – Gene

+1

संयोग से, यह ऐसा कोड प्रतीत होता है जो पार्स पेड़ उत्पन्न कर रहा है जो ग्राफिक रूप से प्रस्तुत किया गया है। हो सकता है कि आप यहां पार्सर को कैसे सेट अप करते हैं, इस बारे में सुराग देख सकते हैं: https://github.com/antlr/antlr4/blob/46b3aa98cc8d8b6908c2cabb64a9587b6b973e6c/tool/src/org/antlr/v4/gui/TestRig.java#L170 – Gene

उत्तर

3

यह समस्या प्लगइन के संस्करण 1.8.2 पर तय की गई थी। यदि आपके पास संस्करण 1.8.2 या बाद का संस्करण है, तो संभवतः आपने इस मुद्दे के किसी अन्य अज्ञात उप-खोज की खोज की है।

हालांकि (जिस मुद्दे पर मैं जिक्र कर रहा हूं उसके आधार पर) पेड़ केवल तभी भिन्न होते हैं जब पार्सिंग में त्रुटि होती है। इसलिए यदि आप त्रुटियों की जानकारी का उपयोग करने में रुचि नहीं रखते हैं, तो आपको ठीक होना चाहिए।

+0

I मैं एक नए संस्करण (1.8.4) का उपयोग कर रहा हूँ। क्या आपके पास उल्लिखित मुद्दे का लिंक है? मुझे यह जानने की ज़रूरत है कि पार्सर गलत इनपुट के साथ कैसे व्यवहार करता है। – predi

+0

मेरे पास लिंक नहीं है, लेकिन यह कहीं भी जिथब पेज पर है https://github.com/antlr/intellij-plugin-v4 – MaanooAk

+0

शायद [यह] (https://github.com/antlr/intellij-plugin -v4/मुद्दों/180)। – predi

संबंधित मुद्दे