2011-06-16 9 views
3

我想將ANTLR定義的語法集成到NetBeans中,並且迄今爲止有效的語法工作正常。但是,如果您輸入任何未在語言中定義的字符(例如,'?'字符),則自定義編輯器會立即崩潰,因爲它無法找到該字符的規則。在ANTLR中捕獲「所有其他」字符

ANTLR在沒有整個詞法分析器崩潰和刻錄的情況下,是否可以捕獲並跳過與規則不匹配的每個字符(並且可能輸出錯誤消息)?我想標記無效字符,跳過它們,並繼續lexing,如:

//some rules + tokens 

invalidCharacter 
    : <<catch all other characters>> 
     {System.out.println("undefined character entered!")} 
    ; 

任何幫助將apprciated。

回答

6

如果你只在詞法分析器內非法字符感興趣,因爲這個簡單的東西可能會爲你做的伎倆:

grammar T; 

@lexer::members { 
    public List<String> errors = new ArrayList<String>(); 
} 

parse 
    : .* EOF 
    ; 

INT 
    : '0'..'9'+ 
    ; 

WORD 
    : ('a'..'z' | 'A'..'Z')+ 
    ; 

SPACE 
    : ' ' {$channel=HIDDEN;} 
    ; 

INVALID 
    : . { 
     errors.add("Invalid character: '" + $text + "' on line: " + 
      getLine() + ", index: " + getCharPositionInLine()); 
     } 
    ; 

正如你所看到的,只有整數和ASCII字符被接受,所有其他字符將導致錯誤被添加到詞法分析器內的List。當解析字符串像"abc 123 ? foo !"與測試類:

import org.antlr.runtime.*; 

public class Main { 
    public static void main(String[] args) throws Exception { 
    TLexer lexer = new TLexer(new ANTLRStringStream("abc 123 ? foo !")); 
    CommonTokenStream tokens = new CommonTokenStream(lexer); 
    tokens.toString(); // dummy call to toString() which causes all tokens to be created 
    if(!lexer.errors.isEmpty()) { 
     for(String error : lexer.errors) { 
     System.out.println(error); 
     } 
    } 
    else { 
     TParser parser = new TParser(tokens); 
     parser.parse(); 
    } 
    } 
} 

會導致以下的輸出:

 
java -cp antlr-3.3.jar org.antlr.Tool T.g 
javac -cp antlr-3.3.jar *.java 
java -cp .:antlr-3.3.jar Main 

Invalid character: '?' on line: 1, index: 9 
Invalid character: '!' on line: 1, index: 15
+0

這似乎做工精細孤立字符,但如果你有很多他們串成它失敗...例如輸入「!!!! ???? ~~~~」 – donnyton 2011-06-16 15:22:54

+0

@donnyton,好吧,對於'n'無效字符,它會創建'n'個不同的消息。如果這不是你想要的,你需要更多地解釋你自己。 – 2011-06-16 15:51:02

+0

當我嘗試將新語法集成到NetBeans中時,它會正確檢測單個無效鍵擊,但當我複製粘貼很多無效字符或打開包含許多無效字符的文件時會崩潰。不過,我已經想出了一個解決方案 - 將INVALID定義爲片段,並制定「無效序列」規則,以更深入地處理它們。 – donnyton 2011-06-16 16:26:48

相關問題