首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >C++中的AI应用:虚拟函数的成本有多高?可能的优化是什么?

C++中的AI应用:虚拟函数的成本有多高?可能的优化是什么?
EN

Stack Overflow用户
提问于 2008-10-01 04:41:50
回答 14查看 6K关注 0票数 16

在我用C++编写的AI应用程序中,

  1. 没有太多的数值计算
  2. 有很多结构经常需要运行时的多态性
  3. ,在计算过程中几个多态性结构相互作用

在这种情况下,有什么优化技术吗?虽然我现在并不关心优化应用程序,但在项目中选择C++而不是Java的一个方面是为了能够更好地利用优化,并能够使用非面向对象的方法(模板、过程、重载)。

具体地说,与虚拟函数相关的优化技术是什么?虚拟函数是通过内存中的虚拟表实现的。有没有办法将这些虚拟表预获取到L2缓存中(从内存/二级缓存获取的成本正在增加)?

除此之外,C++中的数据局部化技术有没有很好的参考资料?这些技术将减少计算所需的将数据提取到L2缓存的等待时间。

更新:还可以查看以下相关论坛:Performance Penalty for InterfaceSeveral Levels of Base Classes

EN

回答 14

Stack Overflow用户

回答已采纳

发布于 2008-10-01 06:17:25

虚函数是非常有效的。假设32位指针,内存布局大约为:

代码语言:javascript
复制
classptr -> [vtable:4][classdata:x]
vtable -> [first:4][second:4][third:4][fourth:4][...]
first -> [code:x]
second -> [code:x]
...

classptr指向通常在堆上的内存,偶尔在堆栈上,并以一个四个字节的指针开始,指向该类的vtable。但要记住的重要一点是,vtable本身并没有分配内存。它是一个静态资源,同一类类型的所有对象都将指向其vtable数组的完全相同的内存位置。对不同实例的调用不会将不同的内存位置拉入L2缓存。

example from msdn显示A类的vtable,其中包含虚拟func1、func2和func3。不超过12个字节。在编译后的库中,不同类的vtable很有可能在物理上是相邻的(你会想要确认这是你特别关心的),这可能会从微观上提高缓存效率。

代码语言:javascript
复制
CONST SEGMENT
??_7A@@6B@
   DD  FLAT:?func1@A@@UAEXXZ
   DD  FLAT:?func2@A@@UAEXXZ
   DD  FLAT:?func3@A@@UAEXXZ
CONST ENDS

另一个性能问题是通过vtable函数调用的指令开销。这也是非常有效的。几乎等同于调用非虚函数。同样来自example from msdn

代码语言:javascript
复制
; A* pa;
; pa->func3();
mov eax, DWORD PTR _pa$[ebp]
mov edx, DWORD PTR [eax]
mov ecx, DWORD PTR _pa$[ebp]
call  DWORD PTR [edx+8]

在本例中,堆栈帧基指针ebp在零偏移处具有变量A* pa。寄存器eax加载了位置ebp处的值,因此它具有A*,而edx加载了位置eax处的值,因此它具有类A vtable。然后ecx加载ebp,因为ecx代表"this“,它现在持有A*,最后调用位置edx+8处的值,这是vtable中的第三个函数地址。

如果这个函数调用不是虚拟的,那么就不需要mov - eax和mov - edx了,但是性能上的差异将是非常小的。

票数 28
EN

Stack Overflow用户

发布于 2008-10-01 17:00:26

draft Technical Report on C++ Performance的第5.3.3节完全致力于虚函数的开销。

票数 11
EN

Stack Overflow用户

发布于 2008-10-01 06:09:28

您是否实际分析并找到了位置,以及需要优化的内容?

当您发现虚函数调用实际上是瓶颈时,请着手实际优化它们。

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/156257

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档