分析效率代码?

Cod*_*313 14 performance profiling code-analysis

您使用哪些工具来确定代码的效率?您是否使用运行统计上大量测试的本土应用程序或某些商业产品?您是否使用自己的知识来测试代码的某些区域,或者使用某种工具来分析代码中的弱点?

Mik*_*vey 28

INSERTED:让我们来看看"统计意义".

假设某处有一个函数调用指令.你不一定能看到它 - 一个类,一个宏,或者一个编译器,可能已经把它搞砸了.附近有相同函数的其他调用,但是这个调用是循环的,或者它的参数是这样的打这个电话需要很长时间.实际上这么多时间,如果这个调用可以花费零时间,那么总执行时间会减少一些,比如说90%.(不可能?根本没有.)时间会精确定位吗?不会.通话图是否会指出它?不会.通话计数会精确定位吗?不是.因为问题不是在功能级别,而是在呼叫指令级别.

不知何故,程序在某个时间点随机停止,并检查其状态.如果指令可以"归零",它会在90%的时间内停止吗?当然 - 概率为90%,指令将在堆栈上精确定位,等待其"工作"完成.

实际上,如果你随机停止20次,那么该指令将在堆栈中平均为18次,标准偏差为+/- 1.3倍.

这有统计学意义吗?你打赌它是.
你需要大量的样品吗?你打赌你没有.

假设百分比很小,例如10%或5%.同样的原则适用.

事实上,无论采集的样本数量如何,任何> 1个样本的指令都具有统计意义,并且是"热点","瓶颈"或任何您想要调用的指令.如果你能删除它,叫它较少,或以某种方式减轻它,它节省时间显著.(有些你不能,比如"call _main",但有些你可以.你只需要找到它们.)

当然我的代码永远不会那么愚蠢,不是吗?那么,证明一下.

好的,现在回到故事...

原始答案:我听说过分析器,回过头来的时候,我认为它们必须非常整洁,但我没有访问它们/它.我正在研究一种嵌入式处理器(8086英特尔芯片),它似乎花了很长时间在显示屏上绘制一些浮点数字.硬件人员建议从他们的充足 - 添加计时器芯片,所以我可以看到事情花了多长时间.然而,在一个周末,我用英特尔"Blue Box"在线仿真器解雇了它,并让它运行起来.虽然它很慢,但我想知道"这到底是做什么的?".所以我只是停下来找出来.PC在浮点库中(没有FP芯片).这并不奇怪,因为它是绘制浮点数,但我想知道更多.所以我(费力地)读取十六进制内存以便跟随调用堆栈.你猜怎么着?它是在绘制数字的过程中,将其除以10,转换为整数,转换回浮点数,减去等等,只是为了得到下一个数字.不用说,有更好的方法可以做到这一点,导致加速大约10倍. 这是一(1)个样本发现的!

另一方面,在68K芯片上,有一些缓慢.同样,一个分析器不可用,但调试器"adb"是,所以虽然它很慢,但我暂停了几次.PC在数学库中,实际上是在32位整数乘法例程中.查找堆栈,我找到了这段代码:

struct {...} a[...];

int i;
for (i = 0; i < ...; ++i){ ... a[i] ... }
Run Code Online (Sandbox Code Playgroud)

那里没有召唤成倍增加 - 发生了什么?事实证明,a[i]编译器必须乘以i数组元素大小.由于i是32位(在该编译器中),它生成对32位乘法例程的调用,并且堆栈精确定位该调用指令.通过声明ishort,循环三倍的速度!

重点是什么?如果您在程序运行缓慢时随机抽取样本,PC会告诉您它正在做什么,但调用堆栈会告诉您原因,并直接引导您解决问题.现在,除非问题非常严重,否则您可能需要采取多个样本.出现在> 1个样本上的任何陈述都是您可以怀疑的陈述.请注意,它甚至可以精确定位语句,指令,而不是像函数一样的大块代码.这种技术可能"快速而肮脏",但它非常有效.

增加:如果反复执行此操作,可以在同一软件中解决问题后的问题.例如,如果您获得3倍的加速,那么之前可能无关紧要的小型性能问题现在会消耗剩余时间的3倍.这使得他们更容易使用样本.您可能必须添加一个临时外循环,以使其运行足够长以进行采样.通过这种方式,我看到复合加速因子超过40倍.

  • 这种技术肯定是有效的.我本周通过另一个Stack Overflow帖子http://stackoverflow.com/questions/375913发现了它,并在我的许多内部和外部用户使用的应用程序上尝试了它.结果是在第一次迭代中总体加速为7次(!) - 从一个特定(典型)数据集上的16.5分钟到2.2分钟. (8认同)
  • @Mike Dunlavey:我只需3-4.到那时已经很清楚了.在下一次迭代中,我花了20次,它给了我一个改变的想法,导致我的应用程序中另一种操作模式(实际上是整个应用程序的最耗时)的3.3倍的加速(http:/ /msquant.sourceforge.net/). (2认同)

Mik*_*els 17

这称为分析.有许多现成的工具可以帮助您确定应用程序瓶颈的位置,适用于各种不同的语言.例如,用于Java 的TPTP工具集可以向您显示性能瓶颈所在的单个方法级别(如果需要).当然,有时您真正需要的只是系统计时器的几个读取,以获得有关代码段的一般概念.