我想解析像这样的数据文件(虚构示例):
Name: bob
Age: 14
-----
Name: alice
-----
对于这个例子,我们假设文件的格式足够复杂,我不想直接对其进行编码。我更喜欢使用 ANTLR 来获得更好的解析器。
问题是:如何使用 ANTLR 将这些数据映射到结构(例如列表)?我不需要完整的语法,只需要解释如何将此类数据映射到数据结构。
最佳答案
我找不到the answer BA-S 在你的问题下发表了评论,所以我开始写一个新的答案。无需太多解释(请阅读其他答案以获取更多信息),这里是一个示例,说明如何使用 ANTLR 将简单输入解析为 List<Person>
.
描述您输入的语法:
grammar T;
parse
: person* EOF
;
person
: Name Word (Age Number)? Separator
;
Name
: 'Name:'
;
Age
: 'Age:'
;
Word
: ('a'..'z')+
;
Number
: ('0'..'9')+
;
Separator
: '-----'
;
Space
: (' ' | '\t' | '\r' | '\n') {skip();}
;
相同的语法,但包括嵌入代码:
grammar T;
parse returns [List<Person> persons]
@init{$persons = new ArrayList<Person>();}
: (person {$persons.add($person.p);})* EOF
;
person returns [Person p]
: Name Word (Age Number)? Separator {$p = new Person($Word.text, $Number.text);}
;
Name
: 'Name:'
;
Age
: 'Age:'
;
Word
: ('a'..'z')+
;
Number
: ('0'..'9')+
;
Separator
: '-----'
;
Space
: (' ' | '\t' | '\r' | '\n') {skip();}
;
还有一个小测试类(带有 class Person
):
import org.antlr.runtime.*;
import org.antlr.runtime.tree.*;
import org.antlr.stringtemplate.*;
public class Main {
public static void main(String[] args) throws Exception {
TLexer lexer = new TLexer(new ANTLRFileStream("test.txt"));
TParser parser = new TParser(new CommonTokenStream(lexer));
java.util.List<Person> persons = parser.parse();
System.out.println(persons);
}
}
class Person {
final String name;
final int age;
public Person(String nm, String num) {
name = nm;
age = num == null ? -1 : Integer.valueOf(num);
}
@Override
public String toString() {
return String.format("{name=%s, age=%d}", name, age);
}
}
哪里test.txt
包含:
Name: bob
Age: 14
-----
Name: alice
-----
如果您现在运行 Main
,将打印以下内容:
[{name=bob, age=14}, {name=alice, age=-1}]
关于antlr - 解析数据文件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9005463/