我正在为我自己的编程语言创建一个编译器,用于在 Minecraft 中创建机器人作为我大学的学期项目。到目前为止,我已经成功地创建了一个带有 ANTLR 的解析器,创建了我自己的抽象语法树结构,并使用 ANTLR 访问者创建了 AST。我处于上下文分析阶段,我目前正在创建符号表并控制结构。我的 SymbolTable 类如下所示:
public class SymbolTable {
private HashMap<String, Symbol> ST = new HashMap<>();
public SymbolTable parent;
public LinkedList<SymbolTable> children = new LinkedList<>();
public String kind;
public String id;
public SymbolTable(String kind, String id){
this.kind = kind;
this.id = id;
}
public void put(String id, Symbol val){
ST.put(id, val);
}
public Symbol get(String id){
if(ST.containsKey(id)) {
return ST.get(id);
}
else{
try {
return parent.get(id);
}
catch(NullPointerException e){
return null;
}
}
}
public boolean contains(String id){
if(ST.containsKey(id)) {
return true;
}
else{
if(parent == null){
return false;
}
return parent.contains(id);
}
}
public String prettyPrint(){
String st = "(TABLE " + this.kind + " " + this.id + " " + ST.toString();
for(SymbolTable nst : children){
st = st.concat(" " + nst.prettyPrint());
}
st = st.concat(")");
return st;
}
public boolean isFunction(){
if(this.kind == "fun"){
return true;
}
else if(!(this.parent == null)){
return this.parent.isFunction();
}
else{
return false;
}
}
}
将变量和函数放入符号表是没有问题的;为此,我使用我的访问者方法,如下所示:
@Override
public Symbol visitStrVarCond(StrVarCondNode node){ return new StringSymbol("var", "string", node.val); }
但是,据我了解,符号表中的符号值(例如变量的值或函数的返回值)也需要存在于符号表中。这也没有问题,这是我已经可以做到的。
不过,我的问题是:
程序员可能使用的一些值在编译时是未知的。它们仅在给定程序的运行时才知道。例如:玩家的当前位置,库存槽中的特定物品等。我的语言有事件,所以例如,如果程序员希望机器人在检测到特定块之前进行挖掘,他们可以这样写:
event block(12:0)
// do stuff
end event
这个特定的事件,块事件,包含块位置等变量。但是,这在编译时是未知的。在将值插入符号表时,如何考虑这样的事情?