FreePascal Information Logo Friend of FreePascal Compiler Title
Articles with Feedback, FPC News Library, PDF Collection, Mail Lists, Books, Newsgroups, IRC Open online discussion areas Research and Tutorials Tools, Compilers and Utilities Blurbs about us, advertising, etc.
Welcome to the FoFPC Research Notes: "FUNCTION vs PROCEDURE"

FUNCTION vs PROCEDURE

by: G.E. Ozz Nixon Jr.
Published: August 2009
©opyright 2009 by Friends of FPC



      Well, I decided to test which is faster calling a function or calling a procedure. And while I am at it, which parameter type is faster, none, var, constant, var of untyped.

    Download Source IconDownload parameter.pas source
Uses
   dxutil_environment;// contains TimeCounter for Windows, Linux and Mac

function A1():Boolean;
begin
   A1:=True;
end;

function B(Var A:Integer):Boolean;
begin
   B:=True;
end;

function C(Const A:Integer):Boolean;
begin
   C:=True;
end;

function D(A:Integer):Boolean;
begin
   D:=True;
end;

function E(var A):Boolean;
begin
   E:=True;
End;

procedure procA1();
Var
   A1:Boolean;

begin
   A1:=True;
end;

procedure procB(Var A:Integer);
Var
   A1:Boolean;

begin
   A1:=True;
end;

procedure procC(Const A:Integer);
Var
   A1:Boolean;

begin
   A1:=True;
end;

procedure procD(A:Integer);
Var
   A1:Boolean;

begin
   A1:=True;
end;

procedure procE(var A);
Var
   A1:Boolean;

begin
   A1:=True;
End;

Var
   Loop:Longint;
   StartTime:Comp;
   I:Integer;

Begin
   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do A1();
   System.Write('A1: ',Trunc(Trunc(TimeCounter)-StartTime));
   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do procA1();
   System.Writeln(' procA1: ',Trunc(Trunc(TimeCounter)-StartTime));

   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do B(I);
   System.Write('B: ',Trunc(Trunc(TimeCounter)-StartTime));
   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do procB(I);
   System.Writeln(' procB: ',Trunc(Trunc(TimeCounter)-StartTime));

   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do C(I);
   System.Write('C: ',Trunc(Trunc(TimeCounter)-StartTime));
   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do procC(I);
   System.Writeln(' procC: ',Trunc(Trunc(TimeCounter)-StartTime));

   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do D(I);
   System.Write('D: ',Trunc(Trunc(TimeCounter)-StartTime));
   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do procD(I);
   System.Writeln(' procD: ',Trunc(Trunc(TimeCounter)-StartTime));

   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do E(I);
   System.Write('E: ',Trunc(Trunc(TimeCounter)-StartTime));
   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do procE(I);
   System.Writeln(' procE: ',Trunc(Trunc(TimeCounter)-StartTime));
end.

     Well running this as is, you will see no matter what operating system you are on, that procedure calls execute (return) faster. Now, if you were into assembly the reason is obvious, but I will state it here anyway - functions require you to push and pop extra information (the result).

     However, the other part that this exercise focused on was different parameter types. Calling a method which takes no parameters of course is the fastest. A1 296ms and procA1 273ms. And you would expect the "Var" type methods to be the slowest. B1 358ms and procB1 309ms. Or even the "Var" of untyped to be the slowest. E1 341ms procE1 310ms. But, the slowest were the const and unspecified methods. C1 362ms C1proc 316ms and D1 366ms D1proc 317ms.

     Old school programmers were always taught to specify "const" to your parameters where possible. However, somewhere along the way with modern compilers and facier CPUs, it appears that rule does not hold true anymore. Now you should be asking yourself, so is it faster to have a procedure which does a var of the result, versus a function that returns the result. The answer is, yes it is much faster! On Linux about 30% faster, it is about 5 times faster!

    Download Source IconDownload which.pas source
Uses
   dxutil_environment;// contains TimeCounter for Windows, Linux and Mac

function A1():AnsiString;
begin
   A1:='';
end;

procedure procA1(var B:AnsiString);
begin
   B:='';
end;

Var
   Loop:Longint;
   StartTime:Comp;
   S:AnsiString;

Begin
   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do A1();
   System.Write('A1: ',Trunc(Trunc(TimeCounter)-StartTime));
   StartTime:=Trunc(TimeCounter);
   For Loop:=1 to 100000000 do procA1(S);
   System.Writeln(' procA1: ',Trunc(Trunc(TimeCounter)-StartTime));

end.


G.E. Ozz Nixon Jr.
 Links and Products we find useful



ButtonGenerator.com
Valid XHTML 1.0 Transitional Internet Map
Programmer's Heaven
grat-i-fi-ca-tion - noun
the state of being gratified; great satisfaction.


"Friends of Free Pascal is, in my view, one of the best things to happen to FPC since the compiler first appeared"

Gary Funk
BoardWatch Magazine
Locations of visitors to this page world map hits counter
Copyright 2009 by 3F, LLC. All rights reserved. Worldwide.
Your request was processed by server #3 in 0.003330 secs.

sponsor
This sponsor helps us with our documentation