i'm using JCL's expression evaluator TEvaluator (a marvelous creation donated by barry kelly). (THANK YOU barry!)
background
i've used the AddFunc method.
function MyFunc:double;
begin
// calculations here
Result:=1;
end;
you can use the AddFunc method to make the function available:
AddFunc('MyFunc', MyFunc);
here's the problem...
i need to call a method on an object instead of a standalone routine.
the reason is that i have a list of objects that provide the values.
say we have a list of vehicle objects. each object has a Weight function. i want to be able to make available each object's weight available for use in the formula.
a silly example but it's easy to explain:
type
TVehicle=class
private
public
function Weight:double;
end;
function StrangeCalculation:double;
var
vehicle:TVehicle;
begin
for iVehicle = 0 to Count - 1 do
begin
vehicle:=GetVehicle(iVehicle);
// E2250 There is no overloaded version of 'AddFunc' that can be called with these arguments
eval.AddFunc(vehicle.Name, vehicle.Weight);
end;
Result:=eval.Evaluate('JeepTJWeight + FordF150Weight * 2');
end;
my options:
AddVar( ) or AddConst( ) -- but that isn't so great because i need to be able to raise an exception if the value is not available.
AddFunc( ) with standalone functions. can't do that because the names of (and number of) variables is unknown until runtime.
modify the object to add a callback if the variable isn't found. i have actually done this but needed to edit a copy of the source to call back to make it do this.
make an AddFunc( ) that's able to use method functions.
option #3 is actually built but an additional AddFunc would be nicer. the trouble is i don't know what method prototype to provide. i thought TMethod would be the way but my knowledge is too limited here... here was my unsuccessful attempt but i still get "E2250 There is no overloaded version of 'AddFunc' that can be called with these arguments" at the eval.AddFunc() call like before.
TFloat64MethodFunc = function(c:pointer): TFloat64;
procedure TEasyEvaluator.AddFunc(const AName: string; AFunc: TFloat64MethodFunc);
begin
FOwnContext.Add(TExprFloat64MethodFuncSym.Create(AName, AFunc));
end;
TExprFloat64MethodFuncSym = class(TExprAbstractFuncSym)
private
FFunc: TFloat64MethodFunc;
public
constructor Create(const AIdent: string; AFunc: TFloat64MethodFunc);
function Evaluate: TFloat; override;
// not using function Compile: TExprNode; override;
end;
thank you for your help!
mp