我正在尝试解析一个虚构语言程序的抽象语法树(AST),具体来说,我正在尝试模拟作用域。例如,进入一个函数时会推入一个新的作用域,当访问者完成对函数的访问时,它会弹出该作用域。其中一个重要方面是,在推入新作用域时,会设置一个指针currentScope
,它指向我们当前查看的作用域。当我们弹出作用域时,这个currentScope
被设置为“外部”:
class Scope:
outer : Scope
inner : Scope
这将在多个步骤中进行,但第一步很重要,它需要构建作用域的整体树。 然而我要问的问题是,如何按照创建顺序遍历这棵树? 例如:
{ // global scope
{ // a
{ // aa
}
{ // ab
}
}
{ // b
}
}
当我再次经过完全相同的节点集时,理论上它们将给我相同的作用域树,但我想保留我们收集和存储每个通行证的所有数据。换句话说,在AST上进行第二或第三次通行时,当我们访问a时,currentScope = a,当我们访问aa时,currentScope = aa。这种可能吗?我对这个想法真的很困惑,整个递归方面真的搞乱了我的头脑,我似乎无法弄清如何做到这一点。
这是我尝试过的内容:
class Scope
outer : Scope
inner : Scope
siblings : []Scope
Scope(outer):
this.outer = outer
push_idx = 0
push_scope()
// set global scope
if current is null
global = new Scope(null)
current = global
return
if current.inner is not null:
// first pass over the AST
if current_pass == 0:
new_scope = new Scope(current)
current.siblings.push(new_scope)
current = new_scope
return
current = current.siblings[push_idx++]
else:
new_scope = new Scope(current)
current.inner = new_scope
current = current.inner
pop_scope()
push_idx = 0
current = current.outer
虽然顺序似乎不正确,我相当确定这是错误的方法。