我有很多
的程序i := i +1;
在其中,我想
inc(i);
看起来好多了。是否有性能差异或函数调用是否只是由编译器内联?我知道这可能与我的应用程序无关,我只是很好奇。
编辑:我做了一些性能测量,发现差异非常小,实际上小到了5.1222741794670901427682121946224e-8!所以真的没关系。优化选项确实没有改变结果。感谢所有提示和建议!答案 0 :(得分:17)
如果启用溢出检查,则会有很大差异。基本上 Inc 不执行溢出检查。按照建议操作并使用反汇编窗口查看打开这些编译器选项时的区别(每个编译器选项都不同)。
如果关闭这些选项,则没有区别。经验法则,当你不关心范围检查失败时使用Inc(因为你不会得到例外!)。
答案 1 :(得分:7)
现代编译器优化代码 inc(i)和i:= i + 1;几乎是一样的。
使用您喜欢的任何一种。
编辑:正如Jim McKeeth纠正的那样:通过溢出检查,存在差异。 Inc不进行范围检查。
答案 2 :(得分:6)
这一切都取决于“我”的类型。在Delphi中,通常将循环变量声明为“i:Integer”,但它也可以是“i:PChar”,它解决了Delns 2009和FPC(我在这里猜测)以下的所有内容的PAnsiChar,以及PWideChar on Delphi 2009和Delphi.NET(也猜测)。
由于Delphi 2009可以执行指针数学,Inc(i)也可以在类型指针上完成(如果它们是在POINTER_MATH打开的情况下定义的)。
例如:
type
PSomeRecord = ^RSomeRecord;
RSomeRecord = record
Value1: Integer;
Value2: Double;
end;
var
i: PSomeRecord;
procedure Test;
begin
Inc(i); // This line increases i with SizeOf(RSomeRecord) bytes, thanks to POINTER_MATH !
end;
正如其他的引用者已经说过的那样:通过开放可以很容易地看到编译器对你的代码做了什么:
观看次数>调试Windows> CPU Windows>拆卸
请注意,OPTIMIZATION,OVERFLOW_CHECKS和RANGE_CHECKS等编译器选项可能会影响最终结果,因此您应该根据自己的喜好进行设置。
关于此问题的提示:在每个单元中,$ INCLUDE控制编译器选项的文件,这样,当.bdsproj或.dproj以某种方式损坏时,您不会丢失设置。 (查看JCL的源代码以获得一个很好的例子)
答案 3 :(得分:3)
您可以在调试时在CPU窗口中对其进行验证。生成的CPU指令对于两种情况都是相同的。
我同意Inc(I);
看起来更好,尽管这可能是主观的。
更正:我刚在Inc:
的文档中找到了这个“在某些平台上,Inc可能会生成 优化的代码,特别适用于 紧紧的循环。“
所以坚持使用公司可能是明智的。
答案 4 :(得分:1)
你总是可以编写两段代码(在不同的程序中),在代码中放置一个断点并比较CPU窗口中的汇编程序。
一般情况下,我会使用inc(i),它显然只被用作某种循环/索引,而且只要1可以使代码更易于维护,就会使用+ 1(即,可能会改变为未来的另一个整数)或者从算法/规范的角度来看更具可读性。
答案 5 :(得分:0)
“在某些平台上,Inc可能会生成优化代码,尤其适用于紧密循环。” 对于像Delphi这样的优化编译器,它并不关心。那是关于旧的编译器(例如Turbo Pascal)