ANTLR を使用しようとしています (3.3 と 3.4 を試しました)。テスト コードを実行しようとすると、奇妙なことが起こります。最初に私の非常に単純なコードを見てください。後で問題を説明します。
テスト文法:
lexer grammar CSVLexer;
Comma
: ','
;
LineBreak
: '\r'? '\n'
| '\r'
;
SimpleValue
: ~(',' | '\r' | '\n' | '"')+
;
QuotedValue
: '"' ('""' | ~'"')* '"'
;
テストコード:
import org.antlr.runtime.*;
public class JMain {
public static void main(String[] args) throws Exception {
String source = "val1,val2,val3";
CSVLexer lexer = new CSVLexer(new ANTLRStringStream(source));
CommonTokenStream tokens = new CommonTokenStream(lexer);
int n = 1;
for (Object o : tokens.getTokens()) {
CommonToken token = (CommonToken) o;
System.out.println("token(" + n + ") = " + token.getText().replace("\n", "\\n"));
n++;
}
}
}
コンパイル:
$ export CLASSPATH=antlr3.jar
$ java org.antlr.Tool CSVLexer.g
$ javac *.java
$ java JMain
最初の問題は、何も印刷されないことです:)。私は Intellij IDEA (10) で作業しており、ここからコードを実行しようとしましたが成功しませんでした (CLASSPATH に ANTLR を使用)。ただし、ブレークポイントをオンint i = 1
にしてデバッグし、続行する前に1〜3秒待つと、機能します! ブレークポイントなしでデバッグ モードで実行すると、実行されません。誰かが私に何が問題なのか説明してもらえますか? ありがとうございました。
編集:
だから私はあなたを入れてみました:
tokens.fill()
直後の
CommonTokenStream tokens = new CommonTokenStream(lexer);
そしてそれはうまくいきました。しかし、その後、CommonTokenStreamコンストラクターのデバッグを開始し (数分)、乗ったときにtokens.fill()
IndexOutOfBoundException が発生しました。どういうわけか、バックグラウンドで何かが何かをしましたが、IDEA に他のスレッドが表示されません。
EDIT2:
問題が解決しました。fill()
最初に呼び出す必要があるようですが、BufferedTokenStream
おそらくこのように使用することを意図していませんでした。私はこのチュートリアルhttp://bkiers.blogspot.com/2011/03/2-introduction-to-antlr.htmlに従いましたが、おそらく著者にとっては何らかの形で機能していました(なぜだろうか)。IntelliJ IDEA デバッガーtoString()
がローカル オブジェクトを呼び出し、それが順番に呼び出されfill()
たため、ブレークポイントを設定したときに機能しました。toString()
改造状態は悪です!