在表达式中使用变量时,编译器如何跟踪变量的声明?
例如,如果我有以下代码:
int num = 1; //declaration
num = 2; //expression
我知道语法树将为声明生成一个分支,为表达式生成一个分支,但是它如何在语义分析器中维护它们之间的连接?
答案 0 :(得分:3)
编译器的语义分析阶段包括处理符号表,顾名思义,该表可跟踪程序中使用的所有符号(名称)。例如,这还允许检测未声明的名称。
因此,当分析器“看到”声明时,它将创建一个新符号(如Symbol(type=Int, offset=0)
)并将其插入到映射name -> Symbol
中。例如,symbol_table["num"] = Symbol(type=Int, offset=0)
。
然后,当分析表达式或语句(在您的示例中为语句)时,编译器可以例如分析其成员的类型。为此,它将查找符号表中使用的名称:
assign_to_symbol = symbol_table["num"]
if assign_to_symbol.type == right_hand_side.type:
DoStuff()
else:
ThatIsAnError()
如果在此范围内没有名称"num"
,则查找失败,从而指示错误。