30

I have a function in my application that needs to return an array. I have found in a couple of places how to do this by declaring the array type, e.g.

type
  TStringArray = array of string; 

And then declaring my function

function SomeFunction(SomeParam: Integer): TStringArray;

My problem is trying to set this up in a form that has both interface and implementation. How do I declare my type and have a function declaration with that type in the interface ?

8
  • 5
    "Array of string" is usually considered "not idiomatic" in Delphi. TStringList is usually preferred. Commented May 27, 2011 at 2:14
  • 1
    I usually use the "DynArray" suffix for naming such type definition, in order to make a distinction between a dynamic and a static array: TStringDynArray = array of string; TStringArray = array[0..(maxInt div sizeof(string))-1] of string; But there is no official convention about it. Commented May 27, 2011 at 6:05
  • 2
    @Warren P: Note that the new FileIO unit uses which is part of the XE RTL uses TStringDynArray extensively. So I don't agree that it is not idiomatic. Especially if you want to return the array and loop over it using an enumerator this is very convenient (see TDirectory.GetFiles for an example). Commented May 27, 2011 at 10:32
  • 3
    @Warren P: One more point: returning a TStringList is even less idiomatic, beacause it violates the "creator is responsible for destruction" principle Commented May 27, 2011 at 10:33
  • 3
    What's the point of this convention? I find for FileName in TDirectory.GetFiles do ... so much more elegant than StrList := TStringList.Create; try TDirectory.GetFiles (StrList); for FileName in StrList do ... finally StrList.Free; end; Are there any disadvantages of the array approach? Otherwise there's no reason not to use it IMHO Commented May 27, 2011 at 13:50

2 Answers 2

42
unit Unit1;

interface

uses SysUtils;

type
  TStringArray = array of string;

function SomeFunction(SomeParam: integer): TStringArray;

...

implementation

function SomeFunction(SomeParam: integer): TStringArray;
begin
  SetLength(result, 3);
  result[0] := 'Alpha';
  result[1] := 'Beta';
  result[2] := 'Gamma';
end;

...

end.

The golden rule is that the interface section of a unit describes the data types used by the unit, and the types, classes and functions (their signatures) that reside in the unit. This is what all other units see. The implementation section contains the implementation of the classes and functions. This is not visible to other units. Other units need to care about the interface of the unit, the 'contract' signed by this unit and the external unit, not the 'implementation details' found in the implementation section.

Sign up to request clarification or add additional context in comments.

Comments

21

If you Delphi is fairly recent, you don't need to declare a new type, by declaring it as TArray<String>.

Example copied and pasted from the answer above:

unit Unit1;

interface

function SomeFunction(SomeParam: integer): TArray<String>;

implementation

function SomeFunction(SomeParam: integer): TArray<String>;
begin
  SetLength(result, 3);
  result[0] := 'Alpha';
  result[1] := 'Beta';
  result[2] := 'Gamma';
end;

end.

1 Comment

TArray<T> (and Generics in general) is not without some problems though, so be careful with it.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.