因为工作关系,要设计一个语法分析器,来做为一个数据分析产品的人机界面。
将所有的分析需求抽象成一系列的命令(cmd),通过一个相对readable的语法将命令组合,后端分析集群接收到这个语法,执行相应操作,返回前端结果。
这样做的由头是因为前端分析需求实在是变化太快,之前的做法是均由程序员coding来实现,费时费力,效率也不高。
这个设想如果能实现,那么,前端的需求就可以即时转化成结果,并也可以由前端人员自行调整。
前后接触了三个语法分析器,javacc,antlr,jparsec。
从stackoverflow上发现的jparsec,有个哥么重点推荐,答案被顶了17次,说jparsec异常简单,我信以为真,跑去研究了半天,复杂的不行,中间抽象的概念晦涩难懂,放弃!
重点说下javacc。
使用javacc可按如下步骤进行,简称我的最佳实践吧^_^
1.写好jjt文件,将语法分析成抽象语法树(AST),标准程序
-
<S_IDENTIFIER> {jjtThis.names.add(token.image);}
2.将AST_Start(root节点)改写,添加如下方法:
-
public class AST_Start extends SimpleNode {
-
public int getType() {
-
return ((SimpleNode) children[0]).id;
-
}
-
/**
-
* Gets the default statement node.
-
*/
-
public Node getStmt() {
-
return children[0];
-
}
-
}
3.根据生成好的AST node进行自定义扩充(关键一步,key step!!),编写相关成员函数,得到相应的如下所示:
-
public class AST_Top extends SimpleNode {
-
/** Gets the options */
-
public String[] getOptions() {
-
return ((AST_IdentList) children[0]).getNames();
-
}
-
/** Gets the fields.*/
-
public String[] getFields() {
-
return ((AST_IdentList) children[1]).getNames();
-
}
-
}
4.这个时候,从文本分析出相关指令。撰写一个class,执行相关实际分析操作,如下所示:
-
class Top implements Plan {
-
private String options[];
-
private String fields[];
-
public Select(AST_Select tree) throws QueryException {
-
-
options = tree.getOptions();
-
fields = tree.getFields();
-
}
-
-
public void execute(){
-
/** do some jobs
-
可以进行真正的操作了
-
*/
-
}
-
}
好了,个人觉得如上布局应该可扩展性还不错,嗯。
阅读(1860) | 评论(0) | 转发(0) |