On 17/10/2011 21:53, Andrew Pennebaker wrote:
> Does Free Pascal have anonymous functions that you can pass around,
> e.g. to a sort(compare : function, arr : array) function?
>
> If not, does anyone know any hacks to accomplish this?
>
> Cheers,
>
> Andrew Pennebaker www.yellosoft.us <http://www.yellosoft.us>
>
Yes:
//you can declare a type :
TMyFunction: function(AMyParam : TType): TOtherType;
// then implement:
function MyFunctionWithArbitraryName(AMyParam: TType): TOtherType;
begin
{do something with AMyParam}
end;
//then (or before, if the TMyFunction is in type declaration section)
function AFunctionUsingTMyFunctionAsArgument(AFunction :
TMyFunction):TWhateverType;
var OtherReturn: TOtherType;
AParameterToAFunction : TType;
begin
{some code}
OtherReturn := AFunction(AParameter);
{other code}
end;
// and finally even
const MYFUNCTIONCOUNT = 1
ArrayOfTMyFunction = array[0..MYFUNCTIONCOUNT-1] of TMyFunction =
(MyFunctionWithArbitraryName);
{it's a static array, so match
the number of elemets}
begin
for {declared somewhere global} i := 0 to MYFUNCTIONCOUNT-1 do
WhateverReturn :=
AFunctionUsingTMyFunctionAsArgument(ArrayOfTMyFunction[i](MyParam));
end.
(Terms and conditions : this is invoked from /dev/mem, some syntax
discrepancies may occur
as my attention moved on from this as it obviously worked)
I have written a dumb CLI interpreter this way ;) recently.
(the function table contains command name as string in a record together with
the function
and the main procedure looks for the name and executes the arbitrary function
when found)
TMyFunctionRecord = record
CLIName: string;
MyFunction : TMyFunction
end;
const ArrayOfCLIFunctions = array[0..CLIFUNCCOUNT-1] of TMyFunctionRecord =
({...});
var CLIFunctionToExecute : TMyFunction;
WhateverReturn : TWhateverType;
begin
for i := 0 to CLIFUNCCOUNT-1 do
if ArrayOfCLIFunctions[i].CLIName = paramstr[1] then
begin
CLIFunctionToExecute := ArrayOfCLIFunctions[i].MyFunction;
break;
end;
WhateverReturn :=
AFunctionUsingTMyFunctionAsArgument(CLIFunctionToExecute(MyParam));
end.
Also the 'anonymous' functions can be implemented in a separate unit which only
exports the
/relevant/ ones in its interface section.
The obvious limitation / safeguard is : you must use the function of declared
type to pass into
the function AFunctionUsingTMyFunctionAsArgument(AFunction : TMyFunction) and
no other type;
(An obvious workaround to that is to use varargs ;) but I did not try that so I
can't tell
whether that would work)
It's not much OOP in action (and may have {obvious for some //not me}
performance penalties but oh well. ;)
L.
_______________________________________________
fpc-pascal maillist - [email protected]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal