Zitat von
oki:
Dynamische Arrays sind
imho Zeiger auf Speicherbereiche.
Korrekt.
Zitat von
oki:
Das Setzen einer Variable auf nil die ein dynamisches Array hält reicht aus um das Array zu "lösche".
Dabei greift hier Compilermagic von Delphi, welche implizit ein SetLength(x, 0) damit aufruft und zuvor, wenn nötig, das Array finalisiert.
Zitat von
oki:
Somit sollte eine Übergabe eines dyn. Arrays in einer Procedure doch die Übergabe eines Zeigers sein. Ist dann überhaupt eine Deklaration als var-Parameter notwendig?
Wenn du var weglässt, erstellt dir Delphi vor Änderungen eine Kopie des Arrays und somit setzt du höchstens die Kopie auf 0.
Mit dem var hingegen legt Delphi dir keine Kopie an sondern übergibt dir den originalen Zeiger auf das Array vom Aufrufer. Somit kannst du das Array auch verändern.
Zitat von
oki:
Das es bei der Übergabe von dyn. Arrays in Procedure und Funktionen zum delphiinternen kopieren kommt ist mir so neu. Zur Not habe ich wieder was dazu gelernt.
Ich müsste hier vllt. nochmal explizit darauf hinweisen, dass ich die Veränderung des Arrays meine - also von NIL setzen bist SetLength(). Ein Veränderung der Arrayinhalte ohne Grössenänderung ist natürlich ohne var möglich, da er die Daten an der Stelle direkt editiert, welche der Zeiger bestimmt.
Delphi-Quellcode:
program ArrayTest;
{$APPTYPE CONSOLE}
uses
Types,
SysUtils;
procedure ChangeContent(AList: TIntegerDynArray);
var
i: integer;
begin
for i := low(AList)
to high(AList)
do
AList[i] := 10 - i;
end;
procedure ChangeArray(AList: TIntegerDynArray);
var
i: integer;
begin
SetLength(AList, 4);
for i := low(AList)
to high(AList)
do
AList[i] := 50 + i;
end;
procedure Test;
var
lTestCaller: TIntegerDynArray;
lInt, i: integer;
begin
SetLength(lTestCaller, 3);
for i := low(lTestCaller)
to high(lTestCaller)
do
lTestCaller[i] := Succ(i);
WriteLn('
content prior ChangeContent():');
for lInt
in lTestCaller
do
WriteLn(lInt);
WriteLn;
ChangeContent(lTestCaller);
WriteLn('
content after ChangeContent() & prior ChangeArray():');
for lInt
in lTestCaller
do
WriteLn(lInt);
WriteLn;
ChangeArray(lTestCaller);
WriteLn('
content after ChangeArray():');
for lInt
in lTestCaller
do
WriteLn(lInt);
end;
begin
try
Test;
ReadLn;
except
on E:
Exception do
Writeln(E.Classname, '
: ', E.
Message);
end;
end.
Ausgabe:
Zitat von
Command Console:
content prior ChangeContent():
1
2
3
content after ChangeContent() & prior ChangeArray():
10
9
8
content after ChangeArray():
10
9
8