tags:

views:

2263

answers:

6

EDIT:

Is there a better of doing this ?

TPendingBets = class(TDataModule)
  private
  public
    function    GetBdy(out IdEvent : Integer                           )                                                           : Boolean; overload;
    function    GetBdy(out IdEvent : Integer; out idBetType : TBetTypes)                                                           : Boolean; overload;
    function    GetBdy(out IdEvent : Integer; out idBetType : TBetTypes; Out TotalOrgStake,Price : Double; out PriceError :Boolean): Boolean; overload;
  end;

implementation

////////////////////

function    TPendingBets.GetBdy(out IdEvent : Integer ): Boolean;
var idBetType : TBetTypes;
    TotalOrgStake,Price : Double;
    PriceError :Boolean;
begin
   result :=  GetBdy(IdEvent,idBetType,TotalOrgStake,Price,PriceError);
end;

////////////////////

function    TPendingBets.GetBdy(out IdEvent : Integer; out idBetType : TBetTypes): Boolean;
var TotalOrgStake,Price : Double;
    PriceError :Boolean;
begin
   result :=  GetBdy(IdEvent,idBetType,TotalOrgStake,Price,PriceError);
end;

////////////////////

function    TPendingBets.GetBdy(out IdEvent : Integer; out idBetType : TBetTypes; Out TotalOrgStake,Price : Double; out PriceError :Boolean): Boolean;
begin
    result :=  false;
    if cdBdy.Eof = False then
    begin
       IdEvent   :=   cdBdy.FieldByName(IdEvent ).AsInteger);
       idBetType :=   TBetTypes(cdBdy.FieldByName(idBetType ).AsInteger);
       //.
       //.
       result := True;
    end;  
end;

NOTE:

As my initial question was not very clear I have removed part of it

+5  A: 

I think the overload solution is quite a good solution, at least it is one. Other programming languages require you to declare functions with different names.

Another approach may be a dynamic array parameter like:

type
  TExtendedDynArray = array of Extended;  // if not already declared elsewhere

function Fn1(out arr: TExtendedDynArray): Boolean;
Uwe Raabe
+2  A: 

In addition to what Uwe wrote (and I agree that overloading is a better solution here; up voted), you should never presume an out parameter to have any value at all at the start of the function. That's what out means.

Craig Stuntz
+1  A: 

You can use overloaded function something like this

function Fn1(Out A:string; B:integer=5) : boolean; overload;

function Fn1(Out A:string) : boolean; overload;

you must to define both functions.

Kipow
I think that would not work, as a call like Fn1(astringvar) is ambigous. The compiler should not accept it.
Uwe Raabe
Yeah, these would not work because if you only specify a string then it couldn't tell which to call.
Jim McKeeth
+9  A: 

Overloading does not mean having 5 copies of the code in the function. You might have 5 functions, but 4 of them just call the main function with the correct parameters.

I generally don't like out parameters. Have you considered returning a record containing all the results?

Fn1Result = record
  A: Extended;
  B: Integer;
  C, D, E, F: Extended
  S: String;
end;

Then declare your function like:

function Fn1: Fn1Result;
begin
  Fn1.A := C_ConstA;
  // etc. . . .
end;

Naturally I am assuming you are not using output parameters as input. Per the Delphi help:

An out parameter, like a variable parameter, is passed by reference. With an out parameter, however, the initial value of the referenced variable is discarded by the routine it is passed to. The out parameter is for output only; that is, it tells the function or procedure where to store output, but doesn't provide any input.

I get a funny feeling you are using output parameters as input parameters. Don't. Pass them as var if you want them to go both ways.

Jim McKeeth
A: 

Default values can only be used for input parameters (that is: By value and const). For var and out parameters, default values are not possible.

As Jim already pointed out: You can avoid duplicating the code by having most overloaded functions call the one which takes all parameters, so they are merely thin layers over the original function. From Delphi 2005 on you can declare them inline, so the compiler might actually generate more efficient code.

dummzeuch
+1  A: 

As Jim showed, you don't need to copy the code around when overloading.

I don't like much to mix parameters with default values and overloading, because (doing it without care) you can create a mess.

Normally, if I have to support a lot of syntaxes:

1) I define a complete signature, with ALL PARAMETERS. Let's call it the 'master' one.

2) All overloads call that one. Or call one to another, but in the end every overload chain must call the 'master' one to execute the task.

For me, overloads are "parameter crunchers" or "translators". Later, if I need something to modify the master behavior, I create new parameters on 'master' (which can have default values - in fact, mostly have).

If I need a overload with the new parameter, I create a new one and it simply pass it to the "master" procedure. The side effect is that the old ones continue to behave the same.

Fabricio Araujo