Login | Register   
LinkedIn
Google+
Twitter
RSS Feed
Download our iPhone app
TODAY'S HEADLINES  |   ARTICLE ARCHIVE  |   FORUMS  |   TIP BANK
Browse DevX
Sign up for e-mail newsletters from DevX


Tip of the Day
Language: Design Patterns
Expertise: Beginner
Mar 19, 1997

Is it possible to re-size arrays at runtime?

Question:
Is it possible to re-size arrays at runtime?

Answer:
I came across an example of how to do one. The author is Ben Licht, who has come up with a brilliant way to do a runtime sized array.

The trick is using a pointer to an array with a size of 1, then allocating memory for the pointer by multiplying the number of items you want in the array by the size of the array type.

Here's a sample unit I've adapted from his example:

{This unit demonstrates how to implement a dynArray}



unit U;



interface



uses

  SysUtils, WinTypes, WinProcs, Classes, Controls, Forms, Dialogs, StdCtrls;

type

  TResizeArr = array[0..0] of string;

  PResizeArr = ^TResizeArr;

  TForm1 = class(TForm)

    Button1: TButton;

    procedure Button1Click(Sender: TObject);

  private

    { Private declarations }

  public

    { Public declarations }

  end;



var

  Form1: TForm1;



  procedure DefineDynArray(var h : THandle;          {Handle to mem pointer}

                           NumElements : LongInt;    {Number of items in array}

                           var PArr : PResizeArr);   {Pointer to array struct}

  procedure TestDynArray;





implementation



{$R *.DFM}



{============================================================================

 Procedure that defines the dynarray. Note that the THandle and Pointer to

 the array are passed by reference. This enables them to be defined outside

 the scope of this procedure.

 ============================================================================}

procedure DefineDynArray(var h : THandle;          {Handle to mem pointer}

                         NumElements : LongInt;    {Number of items in array}

                         var PArr : PResizeArr);   {Pointer to array struct}

begin



  {Allocate Windows Global Heap memory}

  h    := GlobalAlloc(GMEM_FIXED, NumElements * sizeof(TResizeArr));

  PArr := GlobalLock(h);

end;



{============================================================================

 Procedure that uses the DefineDynArray proc. This is pretty useless, but

 provides a good example of how you can access the elements of the 'array'

 once the array is defined.

 ============================================================================}



procedure TestDynArray;

var

  MyArray : PResizeArr;

  I       : Integer;

  str     : String;

  h       : THandle;

begin



  str := '';

  DefineDynArray(h, 10, MyArray); {Define the 'array'}

  for I := 0 to 9 do

    MyArray^[I] := IntToStr(I);

  for I := 0 to 9 do

    str := str + MyArray^[I] + ',';





  ShowMessage(str);

  GlobalUnlock(h); {Must make a call to unlock the memory, then}

  GlobalFree(h);   {free the memory and invalidate the handle}

end;



procedure TForm1.Button1Click(Sender: TObject);

begin

     TestDynArray;

end;



end.



This is a perfect example of one of those programming things that take hours to figure out, but turn out to be amazingly simple.

DevX Pro
 
Comment and Contribute

 

 

 

 

 


(Maximum characters: 1200). You have 1200 characters left.

 

 

Sitemap
Thanks for your registration, follow us on our social networks to keep up-to-date