如何在本地符号Table中表示外部符号的类型信息?

How to Represent Type Information of External Symbols in a local Symbol Table?

有很多关于在源代码解析过程中构建符号 table 的资源,只要符号是本地的即可。但是外在的符号怎么整合,part。他们的类型信息,对于具有导入的语言?

比如说,当前代码(静态类型语言)导入了一个导出一些函数、变量和 类 的模块,这些符号可以直接在当前代码中使用(想想 Java 的 "star" 进口,或 Python 的 from foo import *)。对于当前代码中的符号解析,直接将模块导出的符号包含在当前全局范围内,以便查找它们。

但是模块本身可以导入其他模块,这可能会影响导出的符号,特别是它们的类型。如果你想维护你的符号的类型信息,你可能需要重新进入那些其他模块来查找这些类型,这反过来又可以导入其他相关模块,等等。

虽然此递归分析通常会终止,但这可能会导致将巨大的作用域树添加到本地符号 table,以捕获所有涉及的类型并能够验证 [= 形式的表达式12=]。这也会使导出符号的提前扫描变得更加昂贵。

还有其他方法吗?

我对这种依赖的方法是为每个模块创建一个符号 table。这样的符号 table 可以从任意数量的其他(模块)符号 table 引用(包括它本身,这没有意义,但有可能)。一个简单的列表会在解析符号时注意避免无休止的递归(参见模块)。由于每个模块只有一个 ST,因此您不会创建一个巨大的 ST 树,而是创建一个独特的 ST 图,其节点数最多与所涉及的模块一样多。

有关具体实现,请参阅我的 antlr4-vscode extension,其中我使用 SourceContext class 来涵盖单个文件(模块)的所有详细信息。它包含一个符号 table 和源上下文以及它们的符号 table 相互链接以允许符号(和其他查找)超出当前上下文。然而,在这个实现中我不需要递归停止器,因为 ANTLR4 语法被严格组织为树(tokenVocab,import)。