【问题标题】:How do compilers handle interfaces under the hood? [duplicate]编译器如何在后台处理接口? [复制]
【发布时间】:2018-04-30 10:33:03
【问题描述】:

在高层次上,我理解界面是一种表达方式

就这样吧,我不管怎么做

换句话说,它基本上允许您以声明方式而不是命令方式进行编程。当代码的一部分可以告诉它的其他部分要做什么而不是如何做时,您就可以使您的代码更加灵活。

当涉及到 Java 等高级语言时,我深谙这个概念。

不过,我很好奇编译器 是如何处理接口的。这可能是一个比我意识到的更大的问题。

这是我的理论:它基于 RAM 中的偏移量。

例如,当创建一个实现 ICompare 接口(包括 Compare 方法)的对象时,编译器知道将 Compare 方法放在该对象在 RAM 中开始位置的 16 字节偏移处.事实上,每个实现ICompare 方法的对象在第16 个字节都有它的Compare 方法。这样,当其他代码使用该接口调用Compare 方法时,系统就会知道在该对象的第 16 个字节处执行指令。

这是编译器如何处理接口(在每个对象中使用标准位置)还是使用某种查找表来了解对象的Compare 方法在哪里?还是完全是其他方法?

【问题讨论】:

  • 所以高级别的答案是研究“vtables”。有多种方法可以优化 vtable,但总的来说,这就是您要寻找的概念。
  • 伟大的 cmets,谢谢。这个答案有助于我更好地理解 vtables:stackoverflow.com/a/3555290/2363207。这个评论在 MSDN 链接上很有趣:“.NET IL 定义了一个叫做 MethodImpl 表的东西,它是一个用于类的表,将接口方法映射到方法实现。”

标签: assembly interface compiler-construction


【解决方案1】:

对于其他对此问题感兴趣的人,here 是一个优秀的视频,它直观地解释了 vtables 是如何在 C++ 中实际实现的。对象的前四个字节可以指向一个 vtable,该 vtable 指向用于该特定类的正确方法。

感谢@sircodesalot 的提示。

【讨论】:

  • 具有虚成员函数的对象可以存储在任何地方;静态、自动(堆栈)或堆(动态分配。它总是有一个隐式的vtable 指针作为第一个成员,无论它存储在哪里。另见How do objects work in x86 at the assembly level?
  • 那篇文章的优秀答案,谢谢你的链接。我喜欢答案给你一口大小的sn-ps代码,简洁地证明了一个观点。这表明他们是经过深思熟虑的。谢谢!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-09-25
  • 1970-01-01
  • 1970-01-01
  • 2019-01-27
  • 2012-03-13
  • 2011-06-04
  • 1970-01-01
相关资源
最近更新 更多